# 
# $Header: emagent/scripts/unix/EmctlCommon.pm.template /st_emagent_10.2.0.4.3db11.2.0.2/1 2010/03/11 22:34:49 prapatil Exp $
#
# EmctlCommon.pm
#
# Copyright (c) 2002, 2010, Oracle and/or its affiliates. All rights reserved. 
#
#    NAME
#      EmctlCommon.pm - Common functionality used by emctl
#
#    DESCRIPTION
#      None.
#
#    NOTES
#
#    MODIFIED   (MM/DD/YY)
#    ashomish    10/12/09 - fix bug 8897428
#    ashomish    03/19/09 - fix bug 7664495
#    ajdsouza    02/24/09 - remove DB_UNIQUE_NAME references
#    swexler     04/08/08 - delegate to DBConsole
#    rsamaved    05/30/08 - fix emca map issue
#    rsamaved    05/21/08 - don't use db_unique_name for si db
#    aime        02/19/08 - Pull 4757344 forward
#    swexler     01/23/08 - use DB_UNIQUE_NAME instead of ORACLE_SID
#    apenmets    01/22/08 - branch to st_emagent_10.2.0.4.1db11
#    apenmets    01/07/08 - Updating changes from stpl_emdb_main_gen branch
#    sresrini    12/03/07 - update classpath for 11g jdbc stack
#    svrrao      07/09/07 - Backport svrrao_bug-6141202 from main
#    njagathe    07/02/07 - Backport njagathe_bug-6157933 from main
#    njagathe    06/20/07 - Backport njagathe_bug-6135721 from main
#    dgiaimo     06/13/07 - Fixing backport bug.
#    njagathe    05/09/07 - XbranchMerge njagathe_revert_db11_changes from
#                           st_emagent_10.2.0.1.0
#    njagathe    05/06/07 - Add back ojdbc14.jar
#    njagathe    05/02/07 - XbranchMerge njagathe_jdbc_rename_db11 from
#                           st_emagent_10.2.0.3.1db11
#    vivsharm    04/24/07 - ojdbc14 jar has been sunset
#    dgiaimo     03/30/07 - Fixing bug 5912869
#    dgiaimo     04/05/07 - Backport dgiaimo_bug_5912869 from main
#    dgiaimo     03/30/07 - Fixing bug 5912869
#    cvaishna    03/20/07 - platform specific EMAGENT_RECYCLE_MAXMEMORY setting
#    cvaishna    03/21/07 - XbranchMerge cvaishna_bug-5942315 from main
#    aghanti	 02/19/07 - Bug 5597298 - fixing issues caused due to install
#			    pathname containing the string 'port'
#    svrrao      10/10/06 - Porting Changes, platform specific EMAGENT_RECYCLE_MAXMEMORY setting
#    rsamaved    10/02/06 - dbconsole status url
#    cvaishna    08/18/06 - Fixing JVM recycle memory size on IA64
#    rsamaved    08/31/06 - dbconsole startup fix
#    vivsharm    05/16/06 - for OC4J 10.1.3 changes 
#    smodh       02/20/06 - XbranchMerge smodh_jdbc_emagent from main 
#    shianand    01/05/06 - Backport shianand_bug-4913221 from main 
#    smodh       01/25/06 - Use ojdbc14.jar 
#    shianand    12/20/05 - fix bug 4894781 
#    kduvvuri    09/11/05 - add abbend file processing. 
#    kmanicka    06/21/05 - remove emkey stuff
#    kduvvuri    08/19/05 - bug 4560146. 
#    kmanicka    08/22/05 - fix /dev/null in configemkey
#    shianand    08/10/05 - fix bug 4543290 
#    kduvvuri    08/05/05 - fix 4524126. 
#    kmanicka    06/21/05 - add configEmKey
#    rkpandey    07/15/05 - Bug 4405286: Use File::Copy 
#    sksaha      06/14/05 - Add entry for core signal 
#    shianand    05/20/05 - fix bug 4354597 
#    blivshit    05/19/05 - undo RAC nodename changes per RAC team request 
#                           (venkat.maddali) 
#    gan         03/25/05 - catch local host name 
#    asawant     02/18/05 - Cut over single quote in WINReadPasswd 
#    blivshit    02/18/05 - fix misspelled "topdir" to "topDir 
#    aaitghez    01/26/05 - Porting changes to MAIN line
#    asawant     01/24/05 - getLocalHostName should work in OMS install. 
#    blivshit    01/18/05 - fix NT bug for getLocalRacNode...need to strip 
#                           both CR and LF 
#    vnukal      01/10/05 - adaptable MAX MEMORY 
#    kduvvuri    12/20/04 - add validateTZFix. 
#    blivshit    12/10/04 - add File::spec declaration...this version of Perl 
#                           needs it 
#    blivshit    12/08/04 - change hostname to nodename for rac for oc4jHome 
#    blivshit    12/08/04 - fix open3 problem with stdin 
#    asawant     11/17/04 - getLocalHost errors must go to stderr 
#    aaitghez    11/05/04 - bug 3871127. change timeouts 
#    blivshit    10/27/04 - don't dump errors to stderr for calling lsnodes 
#    blivshit    10/22/04 - use nodename instead of hostname for RAC for state 
#                           directory 
#    asawant     10/19/04 - Cut over EMHOSTNAME to ORACLE_HOSTNAME 
#    vnukal      09/23/04 - reverting pidfile undefinition 
#    vnukal      09/17/04 - pid file obsoletion 
#    vnukal      09/15/04 - adding additional perl tracing 
#    vnukal      09/13/04 - adding tracing routines 
#    asawant     08/24/04 - Adding secure password reading on Windows 
#    gan         08/18/04 - bug 3461755 
#    kduvvuri    07/23/04 - fix getOC4Jhome. 
#    kduvvuri    06/16/04 - add rotate file. 
#    kduvvuri    06/15/04 - set arg to CONSOLE_CFG if no arg is passed to 
#                           getEMOc4j_Home. 
#    aaitghez    06/08/04 - bug 3656322. Cleanup perl warnings 
#    kduvvuri    06/01/04 - create EM_INSTALL_TYPE variable. 
#    asawant     05/14/04 - Fix emctl setpasswd 
#
#

package EmctlCommon;
require Exporter;
use English;
use IPC::Open3;
use Symbol;
use File::Spec;
use Getopt::Long;
use File::Copy;
use File::Temp qw/ tempfile /;
use Config;

our @ISA    = qw(Exporter);
our @EXPORT = qw($EMDROOT $JAVA_HOME $JRE_HOME $ORACLE_HOME $CONSOLE_CFG 
                 $EM_OC4J_OPTS $EMLOC_OVERRIDE $IASCONFIG_LOC $EM_TMP_DIR
                 $STATUS_PROCESS_OK $STATUS_NO_SUCH_PROCESS $STATUS_PROCESS_HANG
                 $STATUS_AGENT_NOT_READY $STATUS_AGENT_ABNORMAL $EMCTL_CORE_SIGNAL
                 $STATUS_PROCESS_PARTIAL $STATUS_PROCESS_UNKNOWN $PERL_BIN 
                 $IAS_NOHUPFILE $IAS_URL $PID_FILE $EMD_HANG_CHECK_STATUS_TIME
                 $AGENT_NOHUPFILE $DB_NOHUPFILE $DB_URL $IN_VOB $IS_WINDOWS
                 $cpSep $binExt $devNull $EMAGENT_TIMESCALE 
		 $NUMBER_AGENT_STATUS_RETRIES $EMAGENT_RECYCLE_SOFTLIMIT
                 $EMAGENT_RECYCLE_DAYS $EMAGENT_MEMCHECK_HOURS $OC4JLOC
                 $EMAGENT_RECYCLE_MAXMEMORY $EMAGENT_MAXMEM_INCREASE
		 $CFS_RAC $HOSTNAME $DEBUG_ENABLED &getEMAgentNameAndTZ
                 $INSTALL_TYPE_IAS $INSTALL_TYPE_CENTRAL $INSTALL_TYPE_AGENT 
                 $INSTALL_TYPE_DB $TIME_BETWEEN_STATUS_CHECK $IAS_LOGDIR
                 &getOC4JHome &getEMHome &getWebUrl &getORMIPort &footer
                 &setReposPasswd &rotateFile &traceDebug &isOmsRecvDirSet
                 $EM_INSTALL_MODULE $EMCTL_UNK_CMD $EMCTL_BAD_USAGE $EMCTL_DONE
                 $FORMFACTOR_BASE $FORMFACTOR_FILE &getTimeouts &getTZFromJava
                 &testCEMDAvail &validateTZAgainstAgent &forceTZRegionValue
                 &updateBlackoutsXmlTS &writeToEMAbbendFile &getOracleUniqueName
                 $EM_ABBEND_MARKER $EM_EXIT_DONT_RESTART $EM_EXIT_THRASH);
                 
# Some Global variables...
$EMCTL_DONE = 0;
$EMCTL_BAD_USAGE = 1;
$EMCTL_UNK_CMD = 2;
$EMCTL_CORE_SIGNAL=9;     # Signal used to kill agent process on hang
$STATUS_PROCESS_OK = 0;   # Indicates that the process is up 
$STATUS_NO_SUCH_PROCESS = 99; # Indicates that the process is not there
$STATUS_PROCESS_HANG = 98; # Indicates that the process is up but unresponsive
$STATUS_PROCESS_UNKNOWN=1; # Indicates an unknown/indeterminate state
$STATUS_AGENT_NOT_READY = 4; # Specific to agent...
$STATUS_AGENT_ABNORMAL  = 7; # Agent tells watch dog to act same as for HANG
$STATUS_PROCESS_PARTIAL=5; # In dual mode system [Console+Agent], either console
                           # or agent is running.

# emctl log file variables
$EMCTL_LOGFILEHANDLE_OPENED = 0;
$EMCTL_LOGFILEHANDLE;

$EM_ABBEND_MARKER="XXXXXXXXXXXXXXXX";
$EM_EXIT_DONT_RESTART=55; #Watch dog exit code when told by the component to 
                          #not restart it. Eg. Agent init failure.
$EM_EXIT_THRASH=56; #Watch dog exit code when there is a thrash.

# variable for catching local host name, rac node
$EM_LOCAL_HOST;
$EM_LOCAL_RAC;

if(defined($ENV{EMCTL_DEBUG}))
{
  $DEBUG_ENABLED=1;
}
$EM_INSTALL_MODULE="CompEM$ENV{CONSOLE_CFG}";


# setup the environment ...
$EMLOC_OVERRIDE="";
$PERL_BIN=$ENV{PERL_BIN};
$OC4JLOC="oc4j/";

if(!defined($ENV{NUMBER_AGENT_STATUS_RETRIES}))
{
    $NUMBER_AGENT_STATUS_RETRIES=2;
}
else
{
    $NUMBER_AGENT_STATUS_RETRIES=$ENV{NUMBER_AGENT_STATUS_RETRIES};
}

# The environment variable, EMAGENT_TIME_FOR_START_STOP
# determines how long the agent start or stop commands
# will wait for the agent to come up or go down.
if(!defined($ENV{EMAGENT_TIME_FOR_START_STOP}))
{
    $EMAGENT_TIME_FOR_START_STOP=30;
}
else
{
    $EMAGENT_TIME_FOR_START_STOP=$ENV{EMAGENT_TIME_FOR_START_STOP};
}

if( !defined($ENV{EMD_HANG_CHECK_STATUS_TIME}))
{
  $EMD_HANG_CHECK_STATUS_TIME=300; # Timeout parameter for emdctl status...
}
else
{
  $EMD_HANG_CHECK_STATUS_TIME=$ENV{EMD_HANG_CHECK_STATUS_TIME};
}

$EM_OC4J_OPTS=$ENV{EM_OC4J_OPTS};
$IASCONFIG_LOC=$ENV{IASCONFIG_LOC};
$JAVA_HOME=$ENV{JAVA_HOME};
$JRE_HOME=$ENV{JRE_HOME};
$EMDROOT=$ENV{EMDROOT};
$ORACLE_HOME=$ENV{ORACLE_HOME};
$CONSOLE_CFG=$ENV{CONSOLE_CFG};

$INSTALL_TYPE_IAS = 0;
$INSTALL_TYPE_CENTRAL = 0;
$INSTALL_TYPE_AGENT = 0;
$INSTALL_TYPE_DB = 0;

#Values for HOST_SID_OFFSET_ENABLED : "" (unset), "host_sid", "host_only"
$HOST_SID_OFFSET_ENABLED=$ENV{HOST_SID_OFFSET_ENABLED};

if($CONSOLE_CFG eq "iasconsole")
{
  # Central Console aka OMS commands are *not* applicable
  # Agent and IASConsole is managed together by a single Process Monitor

  $INSTALL_TYPE_IAS = 1;
}
elsif($CONSOLE_CFG eq "central")
{
  # Central Console aka OMS commands are applicable
  # The Central agent is assumed to be in a different home
  # Since IAS is installed, IASConsole is present and
  # hence central=iasconsole+oms

  $INSTALL_TYPE_CENTRAL = 1;
}
elsif($CONSOLE_CFG eq "agent")
{
  # IASConsole and Central Console commands are *not* applicable

  $INSTALL_TYPE_AGENT = 1;
}
elsif($CONSOLE_CFG eq "dbconsole")
{
  # Same as iasconsole, only thing is dbconsole is now managed
  $INSTALL_TYPE_DB=1;
}
else
{
  # Most likely in views. All commands are applicable, different
  # process monitors.
  $INSTALL_TYPE_CENTRAL = 1;
  $INSTALL_TYPE_AGENT = 1;
  $INSTALL_TYPE_IAS = 1;
  $INSTALL_TYPE_DB = 1;
  $IN_VOB="TRUE";
}

$IS_WINDOWS="";
$binExt = "";
$devNull = "/dev/null";
$cpSep = ":";

if( ($OSNAME eq "MSWin32") or ($OSNAME eq "Windows_NT") )
{
 $IS_WINDOWS="TRUE";
 $binExt = "\.exe";
 $devNull = "nul";
 $cpSep = ";";
}
else
{
 $IS_WINDOWS="FALSE";
}

# This is specific to the EMAGENT
# Set EMAGENT_MEMCHECK_HOURS to 0 to skip memory check
#
if( !defined($ENV{EMAGENT_MEMCHECK_HOURS}))
{
  $EMAGENT_MEMCHECK_HOURS=1;
}
else
{
  $EMAGENT_MEMCHECK_HOURS = $ENV{EMAGENT_MEMCHECK_HOURS};
}

if( !defined($ENV{EMAGENT_RECYCLE_MAXMEMORY}) )
{
  $EMAGENT_RECYCLE_MAXMEMORY=200;
  if ( ($OSNAME eq "dec_osf") )
  {

    $EMAGENT_RECYCLE_MAXMEMORY=1000;
  }
  if( ($OSNAME eq "linux") )
  {
    $EMAGENT_RECYCLE_MAXMEMORY=350;
    
    #for Linux-On-Power
    $EMAGENT_RECYCLE_MAXMEMORY=1000 if ( $Config{archname} =~ /ppc64-linux-thread-multi/ or $Config{'archname'} =~ m/ppc-linux/ );

    #for ia64-linux
    $EMAGENT_RECYCLE_MAXMEMORY=1700 if ( $Config{archname} =~ /ia64-linux-thread-multi/ or $Config{'archname'} =~ m/ia64-linux/ );

    #for z-Linux
    my $z_uname = `uname -a`;
    $EMAGENT_RECYCLE_MAXMEMORY=800 if ( $z_uname =~ m/s390x/i );
  }

  $EMAGENT_RECYCLE_SOFTLIMIT="TRUE"; # when limit not specified explicitly
}
else
{
  $EMAGENT_RECYCLE_MAXMEMORY= $ENV{EMAGENT_RECYCLE_MAXMEMORY};
  $EMAGENT_RECYCLE_SOFTLIMIT="FALSE"; #limit explicitly specified
}

if( !defined($ENV{EMAGENT_MAXMEM_INCREASE}))
{
  $EMAGENT_MAXMEM_INCREASE=1;
}
else
{
  $EMAGENT_MAXMEM_INCREASE= $ENV{EMAGENT_MAXMEM_INCREASE};
}


if( !defined($ENV{EMAGENT_TIMESCALE}))
{
  $EMAGENT_TIMESCALE=1;
}
else
{
  $EMAGENT_TIMESCALE= $ENV{EMAGENT_TIMESCALE};
}

#
# Set EMAGENT_RECYCLE_DAYS to 0 to skip agent recycling based on time
#
if( !defined($ENV{EMAGENT_RECYCLE_DAYS}))
{
  $EMAGENT_RECYCLE_DAYS=0;
}
else
{
  $EMAGENT_RECYCLE_DAYS = $ENV{EMAGENT_RECYCLE_DAYS};
}

# This checks wether the EM_CHECK_STATUS_INTERVAL is enabled or
# not. If it is enabled it is parsed here....
# By default, leave it to 0, so that status is checked every time the
# emwd wakes up. However for Enh. 3082538, the idea is to 
# prolong the status check.

$TIME_BETWEEN_STATUS_CHECK = 0;

if( defined ($ENV{EM_CHECK_INTERVAL}) )
{
  my($multiplier, $SLEEP_TIME) = (1,30);

  my($EM_CHECK_INTERVAL) = $ENV{EM_CHECK_INTERVAL};

  if($EM_CHECK_INTERVAL =~ /[a-gi-ln-rt-zA-GI-LN-RT-Z]/)
  {
    die "Illegal character set defined for $EM_CHECK_INTERVAL. \n";
  }

  if($EM_CHECK_INTERVAL =~ /[sS]$/ )
  {
    my($num, undef) = split /[sS]/,$EM_CHECK_INTERVAL;
    $SLEEP_TIME = $num;
    $multiplier = 1;
  }
  elsif($EM_CHECK_INTERVAL =~ /[mM]$/ )
  {
    my($num, undef) = split /[mM]/,$EM_CHECK_INTERVAL;
    $SLEEP_TIME = $num;
    $multiplier = 60;
  }
  elsif($EM_CHECK_INTERVAL =~ /[hH]$/ )
  {
    my($num, undef) = split /[hH]/,$EM_CHECK_INTERVAL;
    $SLEEP_TIME = $num;
    $multiplier = 3600;
  }
  else
  {
    die "Illegal format defined for EM_CHECK_INTERVAL. Define <number>[sSmMhH] instead of $EM_CHECK_INTERVAL \n";
  }

  $TIME_BETWEEN_STATUS_CHECK = $SLEEP_TIME * $multiplier;

  if($TIME_BETWEEN_STATUS_CHECK < 0)
  {
     print "\nHealth Check for the current component is disabled vide env. variable EM_CHECK_INTERVAL. \n";
  }
}

sub getEMAgentNameAndTZ
{ 
  ($emdPropFile) = @_;
  my ($EMDPROP,$emdPropLine,$tzRegion,$propValue,$propName,$remain,$found,$emdURL,$agentName); 
  
  $repURL = "";
  $tzRegion = "";

  open(EMDPROP,"< $emdPropFile" ) or die "Fatal error can not open:$emdPropFile to look for the property  'agentTZRegion': $!";

  while ($emdPropLine=<EMDPROP>) {
    chomp($emdPropLine);
    #strip all leading  white space characters.
    $emdPropLine =~ s/^\s*//;

    if( ($emdPropLine =~ /^\#/ ) || ( length($emdPropLine) <= 0 ) ) {
    #print "discarding  \"$emdPropLine\" ,since it is a comment \n";
       next;
    }
    ($propName, $propValue , $remain) = split(/\=/ , $emdPropLine , 3);
    #remove leading and trailing white space.
    $propName =~ s/\s*$//;
    $propValue =~ s/^\s*//;
    $propValue =~ s/\s*$//;
    $lengthPropName = length($propName);
    $lengthPropValue = length($propValue);
    if ( ($lengthPropName) > 0  && ($lengthPropValue > 0 ))
    {
       if ( $propName eq "agentTZRegion" )  
       {
         $tzRegion=$propValue;
       }
       if ( ($propName eq "EMD_URL") )
       {
         $emdURL=$propValue;
         if( $emdURL =~ /(.*https?\:\/\/)(.*)(\/emd\/main)/) 
         {
           $agentName=$2;
         }
       } 
    }
  } 
  close(EMDPROP);
  return("$agentName","$tzRegion"); 
}

sub getTZFromJava 
{
  my $rc = 0;
  my $tzret = undef;
  
  my($fh,$tmpfilename) = tempfile(UNLINK => 1, DIR => "$EM_TMP_DIR");
  close $fh; # closing to prevent file sharing violations on Windows
  
  $rc = 0xffff & system("$JRE_HOME/bin/java -DORACLE_HOME=$EMDROOT -DEMHOME=$EMHOME -jar $ORACLE_HOME/jlib/emConfigInstall.jar getSupportedTZ > $tmpfilename 2>&1");
  $rc >>= 8;
  if ($rc == 0 )
  {
    open ($fh,"<$tmpfilename");
    while (<$fh>) {
      $tzret = $_;
    }
    close $fh;
  }

  chop($tzret);
  unlink("$tmpfilename");
  if ($rc != 0)
  {
    printMessage("Failed to get TZ from getSupportedTZ, rc = $rc\n");
  }
  return $tzret;
}

sub forceTZRegionValue 
{
  my ($tzRegion) = @_;
  my $rc = 0;
  
  if($IS_WINDOWS ne "TRUE")
  {
    $ENV{TZ} = $tzRegion;
    my $tzj = getTZFromJava();
    
    if ( $tzRegion ne $tzj ) 
    {
      printMessage("Could not force timezone value to \"$tzRegion\". Found \"$tzj\" instead..");
      $rc = 1;
    }
    else
    {
      $rc = validateTZAgainstAgent($tzRegion);      
    }
  }
  else
  {
    $rc = 1;
  }
  return $rc;
}

#Validates the timezone in emd.properties with that of  agent's time zone.
#
sub validateTZAgainstAgent
{
  my ($tzRegion) = @_;
  my $rc = 0;

  #validate what is in emd.properties is in conformance with 
  #what the agent thinks it should be.
  my($fh,$tmpfilename) = tempfile(UNLINK => 1, DIR => "$EM_TMP_DIR");
  close $fh; # closing to prevent file sharing violations on Windows
  $rc = 0xffff & system("$EMDROOT/bin/emdctl validateTZ agent  $tzRegion > $tmpfilename 2>&1");

  if ( $rc != 0 )
  {
     open ($fh,"<$tmpfilename");
     while (<$fh>) {
       printDMessage ("$_");
     }
     close $fh;
  }
  unlink("$tmpfilename");
  return $rc;
}

#Updates the timestamps in blackouts.xml to match shift in timezone
#
sub updateBlackoutsXmlTS
{
  my ($oldtzRegion, $tzRegion) = @_;
  my $rc = 0;

  #update timestamps in blackouts.xml from values in the old timezone region to 
  #values in the new timezone region
  my($fh,$tmpfilename) = tempfile(UNLINK => 1, DIR => "$EM_TMP_DIR");
  close $fh; # closing to prevent file sharing violations on Windows
  $rc = 0xffff & system("$EMDROOT/bin/emdctl updateBlkoutTS agent $oldtzRegion $tzRegion > $tmpfilename 2>&1");

  if ( $rc != 0 )
  {
     open ($fh,"<$tmpfilename");
     while (<$fh>) {
       printDMessage ("$_");
     }
     close $fh;
  }
  unlink("$tmpfilename");
  return $rc;
}

sub printDMessage()
{
 my ($message) = @_;
 print "----- ".localtime()."::".$message." -----\n";
}
# Sets the FORMFACTOR_BASE and FORMFACTOR_FILE.
# For shutting down without the password, both admin.jar and 
# oc4j.jar handshake on <dir>/opmn/conf/.formfactor file.
# For our standalone consoles, the <dir> is $emHome/sysman
# i.e., the .formfactor is stored in $emHome/sysman/opmn/conf
# and we establish that directory here.
#
sub setFormFactor
{
  my $emHome = shift;

  $formFactorLocation = "$emHome/sysman/opmn/conf";
  $FORMFACTOR_BASE = "$emHome/sysman";  # This is exported out to emctl/emwd/pm's.
  $FORMFACTOR_FILE = "$formFactorLocation/.formfactor"; # exported to emctl

  -e "$FORMFACTOR_BASE" or mkdir "$FORMFACTOR_BASE";
  -e "$FORMFACTOR_BASE/opmn" or mkdir "$FORMFACTOR_BASE/opmn";
  -e "$formFactorLocation" or mkdir "$emHome/sysman/opmn/conf";    
}

# Returns the OC4JHome for the given console type.
sub getOC4JHome
{
 my $consoleType = shift;

 my $oc4jHome = "$EMDROOT/sysman/j2ee"; # default for view...

 if (lc($consoleType) eq "agent" or lc($CONSOLE_CFG) eq "agent" )
 {
   # OC4J is not applicable for agent alone. hence returning
   # empty string for OC4J home.
   $oc4jHome = "";
   return $oc4jHome;
 }
 elsif(lc($consoleType) eq "iasconsole") # OC4JHOME for iasconsole
 {
   #Assume a defined OC4JHome
   $oc4jHome = "$EMDROOT/sysman/j2ee"; # This should be a no op...
 }
 elsif(lc($consoleType) eq "dbconsole") # OC4JHOME for dbconsole
 {
  $moduleName = "CompEM$consoleType";
  $reqPkg = "$moduleName"."\.pm";
  require $reqPkg;
  $obj = $moduleName->new(); 
  $oc4jHome = $obj->getOC4JHome();

 }
 else # If the console type oms.
 {
    # This is the default ...
    $oc4jHome = "$EMDROOT/sysman/j2ee";
 }

 die "OC4J Configuration issue. $oc4jHome not found. \n" unless( -e "$oc4jHome" );

 print "OC4J HOME ==================  $oc4jHome\n"  if $DEBUG_ENABLED;

 return $oc4jHome;
}

# Returns the EMHome for the given console type
sub getEMHome
{
    my $consoleType = shift;
    
    # If the consoleType is undef. default to iasConsole
    $consoleType = "$CONSOLE_CFG" unless defined ($consoleType);
    $consoleType = lc($consoleType);
    
    my $emHome = $EMDROOT;
    
    if($consoleType eq "iasconsole")
    {
	# We initialize the IAS_NOHUPFILE and LOG Dir here...
	$IAS_NOHUPFILE="$emHome/sysman/log/em.nohup";
	$IAS_LOGDIR="$emHome/sysman/log";
	$IAS_LOGFILE="$emHome/sysman/log/em.log";
	$PID_FILE="$emHome/emctl.pid";
    }
    elsif($consoleType eq "dbconsole") # EMHome for dbconsole
    {
      $moduleName = "CompEM$consoleType";
      $reqPkg = "$moduleName"."\.pm";
      require $reqPkg;
      $obj = $moduleName->new();
      $emHome = $obj->getEMHome();
    }
    else
    {	
	# This is the default in all cases except for MAINSA and dbconsole mode
	$emHome = $EMDROOT;
	
	{
            my $topDir = &getLocalHostName();

            print "EM HOME ROOT:  ".$ORACLE_HOME."/".$topDir."\n" if $DEBUG_ENABLED;

	    if ( defined($ENV{EMSTATE}) && $ENV{EMSTATE} ne "" )
	    {
		$emHome = $ENV{EMSTATE};
	    }
	    elsif( $HOST_SID_OFFSET_ENABLED eq "host_sid" )
	    {
		my $oracleSid = $ENV{ORACLE_SID};
		die "Environment variable ORACLE_SID not defined. Please define it. \n" unless defined ($oracleSid);
		
		#use Sys::Hostname;
		#use Net::Domain qw(hostdomain);
		#my $localHost=hostname().".".hostdomain();
		
		$emHome = $ORACLE_HOME."/".$topDir."_".$oracleSid;
		$ENV{EMSTATE} = $emHome;
	    }
            elsif( $HOST_SID_OFFSET_ENABLED eq "host_only" )
            {
                $emHome = $ORACLE_HOME."/".$topDir;
                $ENV{EMSTATE} = $emHome;
            }
	    else # Reinforcing the default ...
	    { 
		$emHome = $EMDROOT;
	    }
	}
    }      
            
    #EM_TMP_DIR is valid only after a call to getEMHome.
    $EM_TMP_DIR = "$emHome";
    # Nohup file when only the agent is running.
    $AGENT_NOHUPFILE="$emHome/sysman/log/emagent.nohup";
    $PID_FILE="$emHome/emctl.pid";    
    die "EM Configuration issue. $emHome not found. \n" unless( -e "$emHome" );

    setFormFactor($emHome);

    print "EMHOME ==================  $emHome\n"  if $DEBUG_ENABLED;
    return $emHome;
}

sub getWebUrl
{
  my $oc4jHome = shift;
  my $emHome = shift;
  my $consoleType = shift;
  $consoleType = lc($consoleType);

  # Ideally we should return the URL for the agent/central oms..
  if(($consoleType eq "agent") or ($consoleType eq "central"))
  {
    return "NULL";
  }

  # Check for the correctness of the oc4jHome location....
  die "Unable to define a url from undefined webapp config location.\n" unless defined($oc4jHome);

  die "Unable to locate web application configuration from $oc4jHome. \n" unless (-e $oc4jHome);

  # Check for the correctness of the emHome location
  die "Unable to locate the EM Application configuration. \n " unless defined($emHome);
  die "Unable to locate the EM Application configuration. \n" unless (-e $emHome);
  
  # Set up the DB URL here...
  my $consolePort = "NULL";
  my $isSecure = "false";
  my $protocol = "http";

  if ($consoleType eq "iasconsole")
  {
    if( -e "$oc4jHome/config/emd-web-site.xml")
    {
      print "Obtaining OC4J Listen Port from $oc4jHome/config/emd-web-site.xml \n" if $DEBUG_ENABLED;
      open(WEBSITECONFIG, "<$oc4jHome/config/emd-web-site.xml");
    }
    else
    {
      die "Unable to determine console port. $oc4jHome/config/emd-web-site.xml not found. $! \n";
    }
  }
  else
  {
    if( -e "$oc4jHome/config/em-web-site.xml")
    {
      print "Obtaining OC4J Listen Port from $oc4jHome/config/em-web-site.xml \n" if $DEBUG_ENABLED;
      open(WEBSITECONFIG, "<$oc4jHome/config/em-web-site.xml");
    }
    elsif( -e "$oc4jHome/config/http-web-site.xml")
    {
      print "Obtaining OC4J Listen Port from $oc4jHome/config/http-web-site.xml \n" if $DEBUG_ENABLED;
      open(WEBSITECONFIG, "<$oc4jHome/config/http-web-site.xml");
    }
    else
    {
      die "Unable to determine console port. $oc4jHome/config/*web-site.xml not found. $! \n";
    }
  }

  my $isProcessingCommentLine = 0;
  my $isMultilineWebSiteTag = 0;
  my $foundPortTag = 0;
  my $foundSecureTag = 0;

  my @xLines = <WEBSITECONFIG>;
  close (WEBSITECONFIG);

  for (my $i = 0; $i < scalar(@xLines); $i++)
  {
    my $line = $xLines[$i];

    if( !$foundPortTag || !$foundSecureTag)
    {
      if($line =~ /\s*\<\!\-\-/)
      {
        #print "\n MATCHED COMMENT LINE START \n";
        if($line !~ /.*\-\-\>/)
        {
          $isProcessingCommentLine = 1;
          #print "\n MULTILINE COMMENT PROCESSING START\n";
        }
        else
        {
          #print " COMMENT LINE END FOUND \n";
        }
      }
      elsif($isProcessingCommentLine)
      {
        if($line =~ /.*\-\-\>/)
        {
          $isProcessingCommentLine = 0;
          #print " MULTILINE COMMENT PROCESSING ENDS \n";
        }
        else
        {
          #print " MULTILINE COMMENT PROCESSING CONTINUES\n";
        }
      }
      elsif($line =~ /\s*\<web\-site/)
      {
        if($line !~ /.*\>/)
        {
          $isMultilineWebSiteTag = 1;
        }
        if($line =~ /port=/)
        {
          #print "\nMatch found on SAME line for port\n";
          my(undef, $portLine) = split /port="/,$line;
          ($consolePort, undef) = split /"/,$portLine;
          $foundPortTag = 1;
        }
        if($line =~ /secure=/)
        {
          #print "\nMatch found on SAME line for secure\n";
          my(undef, $secureLine) = split /secure="/,$line;
          ($isSecure, undef) = split /"/,$secureLine;
          $foundSecureTag = 1;
        }
      }
      elsif($isMultilineWebSiteTag)
      {
        if($line =~ /.*\>/)
        {
          $isMultilineWebSiteTag = 0;
        }
        if($line =~ /port=/)
        {
          #print "\nMatch found on DIFFERENT line for port\n";
          my(undef, $portLine) = split /port="/,$line;
          ($consolePort, undef) = split /"/,$portLine;
          $foundPortTag = 1;
        }
        if($line =~ /secure=/)
        {
          #print "\nMatch found on DIFFERENT line for secure\n";
          my(undef, $secureLine) = split /secure="/,$line;
          ($isSecure, undef) = split /"/,$secureLine;
          $foundSecureTag = 1;
        }
      }
    }
  }

  if(lc($isSecure) eq "true")
  {
    $protocol="https";
  }

  if($consolePort eq "NULL")
  {
    die "Could not determine the correct port. \n";
  }

  -e "$emHome/sysman/config/emd.properties" or die "Unable to determine local host vide $emHome/sysman/config/emd.properties : $!\n";

  open(EMDPROPERTIES, "<$emHome/sysman/config/emd.properties");

  my $hostName;
  while(<EMDPROPERTIES>)
  {
    $emdProp = "EMD_URL";
    if ($consoleType eq "dbconsole" ) {
        # Use REPOSITORY_URL for dbconsole to handle remote OMS
        # configurations for RAC.
        $emdProp = "REPOSITORY_URL";
    }

    if(/^(\s*$emdProp)/) # Search for emdProp
    {
      my (undef, $value) = /([^=]+)\s*=\s*(.+)/;
      my (undef,$machine,undef) = ($value =~ /([^:]+):\/\/([^:]+):([0-9]+)\/.*/);

      if (! defined($machine) )
      {
        die "Unable to determine local host from URL $_ . \n";
      }
      else
      {
          $hostName = $machine;
      }
    }
  }

  close (EMDPROPERTIES);

  my $url="$protocol://$hostName:$consolePort";
  $url=$url."/em/console/aboutApplication" if ($consoleType eq "dbconsole");
  $url=$url."/emd/console/aboutApplication" if ($consoleType eq "iasconsole");

  return $url;
}

sub getORMIPort
{
  my $oc4jHome = shift;

  -e "$oc4jHome/config/rmi.xml" or die "Unable to determine RMI Port vide $oc4jHome/config/rmi.xml : $! \n";

  my $rmiPort = "NULL";

  open(RMICONFIG, "<$oc4jHome/config/rmi.xml");
  while(<RMICONFIG>)
  {
    if(/^(\s*<\s*rmi-server)/)
    {
	 #
	 # Old tag in rmi.xml (OC4J 9.0.4) was:
	 # <rmi-server port="1932">
	 #
	 # New tag in rmi.xml (OC4J 10.1.3) is:
	 # <rmi-server xmlns:xsi="http://a/b/c-d" xsi:text="http://x.y.z/a/b/c-d_0.e" port="1818" ssl-port="1818" schema-major-version="10" schema-minor-version="0">
	 #
	 # New logic:
	 # 1) Split the rmi-server tag on ---> <space>port=<double-quote>
	 # 2) Take the 2nd token which has <port-number><double-quote> and then the rest of the tag.
	 # 3) Split this string on double quote.
	 # 4) Take the first token after this split
	 # 5) Token 1 = port number
	 #
	 my @split_1 = split(" port=\"", $_);
	 my $port_part = $split_1[1];
	 my @split_2 = split("\"", $port_part);
	 $rmiPort = $split_2[0];
     die "ormi port value $rmiPort is erroneous.\n" unless ($rmiPort > 0);
    }
   }
   close(RMICONFIG);

   die "Could not decipher ORMI port from $oc4jHome/config/rmi.xml. It is set to $rmiPort" if ($rmiPort eq "NULL");

   return $rmiPort;
}

#
# Returns the startup and hang timeouts defined in emoms.properties.
# If they're not defined in emoms.properties or if its values are less than the
# default values, then it returns the default values.
# Default value for startupTimeout is 8 minutes
# Default value for hangTimeout is 6 minutes
#
sub getTimeouts
{
  my $emHome = shift;
  my $startupTimeout;
  my $hangTimeout;
  my $defaultStartupTimeout = 480;
  my $defaultHangTimeout = 360;

  if( ! -e "$emHome/sysman/config/emoms.properties")
  {
    $startupTimeout = $defaultStartupTimeout;   # default timeout
    $hangTimeout =  $defaultHangTimeout;   # default timeout

    #Changes for ia64-linux and tru64 and lnx390

    $hangTimeout = 600 if ($OSNAME eq "dec_osf" or $Config{archname} =~ /s390x-linux/);
    
    my @rarray = ($startupTimeout, $hangTimeout);
    return @rarray;
  }

  -e "$emHome/sysman/config/emoms.properties" or die "Unable to locate file $emHome/sysman/config/emoms.properties : $!\n";

  open(EMOMSPROPERTIES, "<$emHome/sysman/config/emoms.properties");

  while(<EMOMSPROPERTIES>)
  {
    if(/^(\s*emctl.watchdog.startup_timeout)/) # Search for emctl.watchdog.startup_timeout...
    {
      my (undef, $value) = /([^=]+)\s*=\s*([0-9]+).*/;
 
      if ( defined($value) )
      {
        $startupTimeout = $value;
        if ( defined($hangTimeout) )
        {
          last;              #exit the loop, both timeouts have been read
        }
      }
    }

    if(/^(\s*emctl.watchdog.hang_timeout)/) # Search for emctl.watchdog.hang_timeout...
    {
      my (undef, $value) = /([^=]+)\s*=\s*([0-9]+).*/;
 
      if ( defined($value) )
      {
        $hangTimeout = $value;
        if ( defined($startupTimeout) )
        {
          last;              #exit the loop, both timeouts have been read
        }
      }
    }
  } # end of while loop

  close (EMOMSPROPERTIES);

  if (!defined($startupTimeout) or $startupTimeout<$defaultStartupTimeout)
  {
     $startupTimeout = $defaultStartupTimeout;   # default timeout
  }

  if (!defined($hangTimeout) or $hangTimeout< $defaultHangTimeout)
  {
     $hangTimeout =  $defaultHangTimeout;   # default timeout

     #Changes for ia64-linux and tru64 and lnx390

     $hangTimeout = 600 if (($OSNAME eq "dec_osf" or $Config{archname} =~ /s390x-linux/) and $hangTimeout<600);
 
  }

  if ($DEBUG_ENABLED)
  {
    print "Startup timeout: $startupTimeout \n";
    print "Hang detection timeout: $hangTimeout \n";
  }

  my @rarray = ($startupTimeout, $hangTimeout);
  return @rarray;
}

# get the RAC local node by calling lsnodes or the Oracle version of that
sub getLocalRACNode
{
  return ($EM_LOCAL_RAC) if (defined $EM_LOCAL_RAC);

  my $localNode = "";
  my $cmd;
  my $lsnodesDir;

  if (defined($ENV{CRS_HOME}) and ($ENV{CRS_HOME} ne "#CRS_HOME#"))
  {      
     $lsnodesDir = $ENV{CRS_HOME}."/bin/olsnodes"."$binExt";
  } else {
     $lsnodesDir = $ORACLE_HOME."/bin/lsnodes"."$binExt";
  }
  $cmd = "$lsnodesDir"." -l";

  print "CRSHOME:  ".$ENV{CRS_HOME}."\n" if $DEBUG_ENABLED;
  print "lsnodes CMD:  ".$cmd."\n" if $DEBUG_ENABLED;

  if (not -e "$lsnodesDir")
  {
     print "Missing ".$lsnodesDir." for RAC\n" if $DEBUG_ENABLED;
  } else {
    my ($pid, $cmdout, $cmderr, $cmdstatus);
    local *NULL;
    my $null_file = File::Spec->devnull();
    open (NULL, $null_file) or confess("Cannot read from $null_file: + $!");

    $pid =  open3("<&NULL", $cmdout, $cmderr, "$cmd");
    $pid = waitpid $pid, 0;
    $cmdstatus = ($? >> 8);
        
    #  PORTING NOTE:  for NT, need to strip both CR and LF !!!
    chomp($localNode = <$cmdout>);
    $localNode =~ s/^\s+|\s+$//;

    print "OUT: *".$localNode."*\n" if $DEBUG_ENABLED;
    print "ERROR: ".<$cmderr>."\n" if $DEBUG_ENABLED;

    close($cmdout);
    close($cmderr);

    if ($cmdstatus != 0) {
        print "lsnodes command failed!  Status: ".$cmdstatus."\n" if $DEBUG_ENABLED;
        $localNode = "";   
		my $localHost = &getLocalHostName();
        print "Using getLocalHostName()\n" if $DEBUG_ENABLED;
        if (defined $localHost)
        {
           $localHost  =~ s/\..*//;
           if(defined $localHost)
           {
               $localNode=lc($localHost);
           }
           print "Using Stripped domain local host name $localNode \n" if $DEBUG_ENABLED;
        }

    }
  }

  $EM_LOCAL_RAC = $localNode;

  return $localNode;
}

# Gets the canonocal hostname of localhost for DBConsole.
# Overriding variable ORACLE_HOSTNAME is looked up in the java code itself...
sub getLocalHostName
{
  return $EM_LOCAL_HOST if (defined $EM_LOCAL_HOST) ;

  # Because in a GC install we don't ship emConfigInstall.jar (the one
  # available in $OH/jlib is from the IAS install and is old) we use
  # TargetInstaller from emCORE.jar. Note that in a DBConsole install we will
  # continue to use emConfigInstall.jar because emCORE.jar is not available
  # in $OH/j2ee/OC4J_EM...
  my $localHostCmd = "$JAVA_HOME/bin/java -DORACLE_HOME=$EMDROOT ".
                     "-classpath ".
                     "$ORACLE_HOME/j2ee/OC4J_EM/applications/em/em/WEB-INF/lib/emCORE.jar".
                     "$cpSep".
                     "$ORACLE_HOME/sysman/jlib/log4j-core.jar".
                     "$cpSep".
                     "$ORACLE_HOME/jlib/emConfigInstall.jar ".
                     "oracle.sysman.emSDK.conf.TargetInstaller getlocalhost";


  my $localHost = `$localHostCmd`;

  chomp($localhost);
  $localHost=~ s/^\s+|\s+$//;

  if ($DEBUG_ENABLED)
  {
    print("Hostname: '$localHost'\n");
  }

  $EM_LOCAL_HOST = $localHost;

  return($localHost);
}

# subroutine to display footer
sub footer()
{
  $EMHOME = getEMHome($ENV{CONSOLE_CFG});
  print "------------------------------------------------------------------\n";
  print "Logs are generated in directory $EMHOME/sysman/log \n";
}

######################################################################
# WINReadPasswd()
# prompt: The message to be displayed before the password is read 
# return: user input
# Comment: Do not call this routine directly, instead call promptUserPasswd().
# This routine is only for Windows systems only.
######################################################################
sub WINReadPasswd
{
  my ($prompt) = @_;
  my $passwd = "";
  my $lineCnt = 0;
  my $finaPwd;
  my $cs = $clsSeparator;

  my $emConsoleMode = &SecureUtil::getConsoleMode();
  my $emAgentMode   = &SecureUtil::getAgentMode();
  my $CLASSPATH     = "$ORACLE_HOME/sysman/jlib/emagentSDK.jar";
  
  if ($emConsoleMode ne "")
  {
    $CLASSPATH = &SecureUtil::getConsoleClassPath($emConsoleMode);
  }
  else
  {
    if ($emAgentMode ne "")
    {
      $CLASSPATH = &SecureUtil::getAgentClassPath();
    }
  }

  eval
  {
    open GETPWD, "$JAVA_HOME/bin/java -classpath $CLASSPATH " .
                 "oracle.sysman.util.winUtil.WinUtil -readPasswd " .
                 "\"$prompt\" -invertFileHandles |";
    while(<GETPWD>)
    {
      $passwd .= $_;
      $lineCnt++;
    };
  };
  if($passwd eq "")
  {
    die("Failed executing java!\n");
  }
  
  unless(($lineCnt == 1) && (($finalPwd) = $passwd =~ m/Password='(.*)'\n$/o))
  {
    die("Failed parsing password returned from Java.\n$passwd\n");
  }
  return($finalPwd);
}


# Added to fix bug 4894781 for Internal Process Synchronization of
# OUI Java process and emctl command's Java process
sub WINReadPasswds
{
  my (@prompt)    = @_;
  my $promptlen   = scalar(@prompt);
  my $promptArgs  = "";

  for($i =0; $i <$promptlen; $i++)
  {
    chomp($prompt[$i]);
    $promptArgs .= " \"$prompt[$i]\" ";
  }

  my @passwd ;
  my @finaPwd;
  my $cs      = $clsSeparator;
  my $lineCnt = 0;

  my $emConsoleMode = &SecureUtil::getConsoleMode();
  my $emAgentMode   = &SecureUtil::getAgentMode();
  my $CLASSPATH     = "$ORACLE_HOME/sysman/jlib/emagentSDK.jar";

  if ($emConsoleMode ne "")
  {
    $CLASSPATH = &SecureUtil::getConsoleClassPath($emConsoleMode);
  }
  else
  {
    if ($emAgentMode ne "")
    {
      $CLASSPATH = &SecureUtil::getAgentClassPath();
    }
  }
  eval
  {
    open GETPWD, "$JAVA_HOME/bin/java -classpath $CLASSPATH " .
                 "oracle.sysman.util.winUtil.WinUtil -readPasswds " .
                 "-invertFileHandles $promptArgs |";
    while(<GETPWD>)
    {
      $passwd[$lineCnt] = $_;
      $lineCnt++;
    }
  };

  if(@passwd eq "" and $lineCnt <$promptlen )
  {
    die("Failed executing java!\n");
  }

  for ($i =0; $i <$promptlen; $i++)
  {
    chomp ($passwd[$i]);
    if ($passwd[$i] =~ m/Password:$i='(.*)'/)
    {
      $finalPwd[$i] = $1;
    }

  }
  return(@finalPwd);
}



######################################################################
# promptUserPasswd()
# prompt for user/passwd input
# return: user input
# Comment: This is how it should look once we get Win32::Console in the
#          standard perl distribution.
#            my $STDIN = new Win32::Console(STD_INPUT_HANDLE);
#            defined($STDIN) or die "Failed to create Win32::Console object!\n";
#            my $origMode = $STDIN->Mode();
#            $STDIN->Mode(&ENABLE_LINE_INPUT | &ENABLE_PROCESSED_INPUT);
#            $password=<STDIN>;
#            $STDIN->Mode($origMode);
#          ---
#          Alternatively, if we get ReadKey() (also Win32 specific):
#            ReadMode('noecho');
#            $password = ReadLine(0);
#            ReadMode('normal');
######################################################################
sub promptUserPasswd
{
   my ($prompt) = @_;
   my $password;
   if($IS_WINDOWS eq "FALSE")
   {
     print $prompt;
     system "stty -echo";
     $password=<STDIN>;
     system "stty echo";
     print "\n";
   }
   else
   {
     $password = WINReadPasswd($prompt);
   }
   chomp ($password);
   return $password;
}


# Added to fix bug 4894781 for Internal Process Synchronization of
# OUI Java process and emctl command's Java process
sub promptUserPasswds
{
   my (@prompt)  = @_;
   my $len = scalar(@prompt);
   my @password;

   if($IS_WINDOWS eq "FALSE")
   {
     for ($j =0; $j <$len; $j++)
     {
       $password[$j]= promptUserPasswd($prompt[$j]);
     }
   }
   else
   {
     @password = WINReadPasswds(@prompt);
   }
   return @password;
}


######################################################################
# setReposPasswd()
#   Set the repostory password in emoms.properties. The password is obfuscated 
# before it is written to the file.
######################################################################
sub setReposPasswd()
{
  $EMHOME = getEMHome($ENV{CONSOLE_CFG});
  $CLASSPATH = "$ORACLE_HOME/sysman/jlib/emCORE.jar"."$cpSep".
               "$ORACLE_HOME/sysman/jlib/emagentSDK.jar"."$cpSep".
               "$ORACLE_HOME/sysman/jlib/log4j-core.jar"."$cpSep".
               "$ORACLE_HOME/j2ee/OC4J_EM/applications/em/em/WEB-INF/lib/emCORE.jar"."$cpSep".
               "$ORACLE_HOME/j2ee/OC4J_EM/applications/em/em/WEB-INF/lib/emagentSDK.jar"."$cpSep".
               "$ORACLE_HOME/j2ee/OC4J_EM/applications/em/em/WEB-INF/lib/log4j-core.jar"."$cpSep".
               "$ORACLE_HOME/jlib/ojmisc.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-mapping.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-translation.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/ojdbc5dms.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-net-ee.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-utility.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-collation.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-net.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-internal.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-servlet.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-lcsd.jar"."$cpSep".
	       "$ORACLE_HOME/oc4j/jdbc/lib/orai18n-tools.jar"."$cpSep".
               "$ORACLE_HOME/oc4j/lib/dms.jar"."$cpSep".
               "$ORACLE_HOME/oc4j/jdbc/lib/orai18n.jar";

  my $newPasswd = promptUserPasswd("Please enter new repository password: ");
  if($newPasswd eq '')
  { 
    # User hit enter without typing anything
    die "Invalid password!\n";
  }
  open(SETPWD, "| $JAVA_HOME/bin/java -classpath $CLASSPATH ".
                  "-DEMSTATE=$EMHOME oracle.sysman.emSDK.conf.ConfigManager ".
                  "-setPasswd >$devNull");
  print SETPWD "$newPasswd";
  close(SETPWD);
  print("Repository password successfully updated.\n");
}

sub rotateFile 
{
    my ($i,$file, $maxbakups,$tmpfile,$tmpfile2);
    ($file, $maxbakups) = @_;
    
    if( -e $file.".".$maxbakups )
    {
	unlink ($file.".".$maxbakups);
    }

    for($i=$maxbakups -1 ; $i >=1 ;$i--) 
    {
	my $nextindex = $i + 1;
	$tmpfile = $file.".".$i;
	$tmpfile2 = $file.".".$nextindex;

	if( -e $tmpfile) 
        {
	    rename($tmpfile,$tmpfile2);
	}
    }
    copy($file,$file."."."1");
}

sub traceDebug
{
 my ($message) = @_;

 if(not defined $EMCTL_LOGFILE) {
   $EMCTL_LOGFILE = getEMHome()."/sysman/log/emctl.log";
 }

 if($EMCTL_LOGFILEHANDLE_OPENED == 0) {
   $EMCTL_LOGFILEHANDLE_OPENED =1;
   unless(open ($EMCTL_LOGFILEHANDLE,">>$EMCTL_LOGFILE")) {
     warn "Unable to open file for logging. $EMCTL_LOGFILE: $!\n";
     return;
   }
 } 

 print $EMCTL_LOGFILEHANDLE "$PID :: ".localtime()."::".$message."\n";
}

sub writeToEMAbbendFile
{
  my ($abbendFile, $message ) = @_;
 
  open(ABBENDFILE, ">>$abbendFile");

  print  ABBENDFILE  "$message\n";

  close ABBENDFILE;
}

#
# Sub routine to test the availibility of CEMD
#
sub testCEMDAvail()
{
    if ((not -e "$EMDROOT/bin/emdctl"."$binExt") or  (not -e "$EMDROOT/bin/emagent"."$binExt"))
    {
        die "Missing either emdctl$binExt or emagent$binExt from $EMDROOT/bin.\n";
    }
    # Change current directory to sysman/emd so cores are generated at that
    # location and are easier to find in cust env.
    chdir("$EMHOME/sysman/emd");
}

# Determine if omsRecvDir is set in emd.properties
# If it is, return 1
# If it is present but commented, return 0
#
# Note: currently if omsRecvDir is not present, return 1
#       This is temporary until omsRecvDir is set in
#       emd.properties out-of-box.  
#
sub isOmsRecvDirSet
{
    my ($emHome) = getEMHome();
    $filename = "$emHome/sysman/config/emd.properties";
    -e "$filename" or die "Unable to locate file $filename : $!\n";

    if ($DEBUG_ENABLED) {
	print ("isOmsRecvDirSet: emd properties filename = $filename\n");
    }
    
    open (EMD_PROP, $filename);
    @lines = <EMD_PROP>;
    
    $recvDirSet = 0;
    $recvDirCommented = 0;
    
    foreach $line (@lines) {
	if ($line =~ /^\#+ *omsRecvDir/) {
	    # omsRecvDir set but commented
	    $recvDirCommented = 1;
	}
	elsif ($line =~ /^ *omsRecvDir/) {
	    # omsRecvDir set
	    $recvDirSet = 1;
	}
    }

    if (!$recvDirCommented && !$recvDirSet) {
	# omsRecvDir not present, return 1 to support current default
        # Todo: when omsRecvDir is set in emd.properties by default,
        #       need to return 0 here
	$recvDirSet = 1;
    }
    
    close (EMD_PROP);

    return $recvDirSet;
}

sub getOracleUniqueName
{
  my $oracleHome       = $_[0];
  my $oracleSid        = $_[1];
  chomp($oracleHome);
  chomp($oracleSid);

  my $myFile = "$oracleHome/sysman/config/emca.map";

  open(FILE, $myFile) or return getOracleUniqueNameFromEnv(); 
  my @linesRead = <FILE>;

  #parse with ":" and get dbunique name, file will have line sid : dbUniquename
  my $sid, $unique_name, $unqname;
  foreach $_ (@linesRead)
  {
    $_ =~ s/ //g;
    ($sid,$unique_name) = split(/:/, $_);
    chomp($sid);
    chomp($unique_name);
    if ($sid eq $oracleSid)
    {
      $unqname = $unique_name;
      last;
    }
    elsif ($IS_WINDOWS eq "TRUE") #for windows ignore case
    {
		if (lc($sid) eq lc($oracleSid))
		{
			  $unqname = $unique_name;
			  last;
		}
   
    } 
    
  }
  close($myFile);

  if (defined($unqname) && $unqname ne "")
  {
    return $unqname;
  }
  else
  {
    return getOracleUniqueNameFromEnv();
  }
}

sub getOracleUniqueNameFromEnv()
{
  if (defined $ENV{ORACLE_UNQNAME} && $ENV{ORACLE_UNQNAME} ne "")
  {
    return $ENV{ORACLE_UNQNAME};
  }

  return;
}

# All modules return something. By convention it is : 
1;
