# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
#
# Copyright 2005-2008 Sun Microsystems, Inc. All rights reserved. 
#
# The contents of this file are subject to the terms of the GNU General Public
# License Version 3("GPL")(the "License").
# You may not use this file except in compliance with the License.
#
# You can obtain a copy of the License at
# https://common-agent-container.dev.java.net/bootstrap/legal/license.txt or
# www/bootstrap/legal/license.txt.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# When distributing the software, include this License Header Notice in each
# file and include the License file at www/bootstrap/legal/license.txt.
#
# Sun designates this particular file as subject to the "Classpath" exception
# as provided by Sun in the GPL Version 3 section of the License file that
# accompanied this code.
#
# If applicable, add the following below the License Header, with the fields
# enclosed by brackets [] replaced by your own identifying information:
#     "Portions Copyrighted [year] [name of copyright owner]"
#


# script functions list:
#
# cacao_create_core_instances : create core defaults instances
# cacao_add_config            : add a property into cacao.properties with
#                               its template's value if it doesn't exist
# cacao_update_config         : update a property from cacao.properties with
#                               its template's value
# cacao_update_java_flags     : modify a java flag inside cacao.properties
# cacao_do_sys_config          : create core default instances and 
#                                configure the startup management for all instances
# cacao_create_install_properties_file : Create an install properties file and
#                                        write into it an install id
# cacao_do_sys_unconfig        : stop all the instances and unconfigure the startup management
# cacao_mark_as_configured     : mark cacao as configured 
# cacao_mark_as_unconfigured   : mark cacao as unconfigured
# cacao_parse_version          : returns a 3uple x y z according to passed version string argument
# cacao_get_version_from_file  : returns version property from file
# cacao_check_if_lower         : validate versions ids and check order
# cacao_is_install_configured  : tell if cacao is configured or not


#------------------------------------------------------------------------------
# cacao_mark_as_unconfigured
#
# DESCRIPTION :
# mark cacao as configured (touch the configured file)
# 
# PARAMETERS :
# none
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_mark_as_configured() {
    
    installed_version=`cacao_get_property "${CACAO_VERSION_KEY}" \
        "${cacao_template_config_dir}/private/cacao.properties"`
    retval=$?
    if [ $retval -ne ${CACAO_CR_SUCCESS} ]
    then
	${TOUCH} ${cacao_configured_file} 2>/dev/null
    else
	${ECHO} ${installed_version} > ${cacao_configured_file} 2>/dev/null
    fi
    if [ ${?} -ne 0 ]
    then
        return ${CACAO_CR_ERROR}
    fi
    
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_mark_as_unconfigured
#
# DESCRIPTION :
# mark cacao as unconfigured (remove configured file)
# 
# PARAMETERS :
# none
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_mark_as_unconfigured() {
     if [ -f "${cacao_configured_file}" ]
     then
        ${RM} -f ${cacao_configured_file}
        if [ ${?} -ne 0 ]
        then
            return ${CACAO_CR_ERROR}
        fi
     fi
     return ${CACAO_CR_SUCCESS}
}


#------------------------------------------------------------------------------
# cacao_parse_version
#
# DESCRIPTION :
# returns a 3uple x.y.z according to passed version string argument
# 
# PARAMETERS :
# version string
# 
# RETURN CODE: 
# None.
# 
# OUTPUT:
# x.y.z 3uple (x, y & z can be empty strings)
#------------------------------------------------------------------------------
cacao_parse_version() {
    vstr=$1
    # Try to handle rev like x.y,REV=z.t
    configured_version_old_rev=`${ECHO} $vstr | ${AWK} -F, '{print $2}' | ${SED} -e 's/REV=//'`
    # Old cacao rev numbers
    if [ -n "${configured_version_old_rev}" ]; then
	configured_version_major=`${ECHO} $vstr | ${AWK} -F, '{print $1}' | ${AWK} -F. '{print $1}'`
	configured_version_minor=`${ECHO} $vstr | ${AWK} -F, '{print $1}' | ${AWK} -F. '{print $2}'`
    else
	# New version x.y.z or empty file
	configured_version_major=`${ECHO} $vstr | ${AWK} -F. '{print $1}'`
	configured_version_minor=`${ECHO} $vstr | ${AWK} -F. '{print $2}'`
	configured_version_old_rev=`${ECHO} $vstr | ${AWK} -F. '{print $3}'`
    fi
    ${ECHO} "${configured_version_major}.${configured_version_minor}.${configured_version_old_rev}"
}

#------------------------------------------------------------------------------
# cacao_get_version_from_file
#
# DESCRIPTION :
# returns a 3uple x.y.z according to passed version string argument
# 
# PARAMETERS :
# configuration file
# 
# RETURN CODE: 
# Error or success.
# 
# OUTPUT:
# version string
#------------------------------------------------------------------------------
cacao_get_version_from_file() {
    # Bad installation case
    if [ ! -f "$1" ]; then
	cacao_print_error_message "${CACAO_MSG_ERROR_FILE_CAT}" "$1"
	cacao_exit ${CACAO_CR_ERROR}
    fi
    l_version=`cacao_get_property "${CACAO_VERSION_KEY}" \
	"$1"`
    retval=$?
    if [ $retval -ne ${CACAO_CR_SUCCESS} ]; then
	cacao_print_error_message "${CACAO_MSG_ERROR_PROPERTY_NOT_FOUND}" "${CACAO_VERSION_KEY}"
	cacao_exit ${CACAO_CR_ERROR}
    fi
    ${ECHO} "${l_version}"
}

#------------------------------------------------------------------------------
# cacao_check_if_lower
#
# DESCRIPTION :
# validate versions ids and check order
# 
# PARAMETERS :
# str1 & str2
# 
# RETURN CODE: 
# 3 if non valid id strings
# 0  if equals
# 1  if v1 > v2
# 2 if v1 < v2
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_check_if_lower() {
    v1=$1
    v2=$2

    # Strings can not be empty
    if [ -z "$v1" ] || [ -z "$v2" ]; then
	return 3
    fi
    # Strings can not contain non digit chars
    valid=`${ECHO} "${v1}${v2}" | ${SED} -e 's/[0-9\.]//g'`
    if [ -n "${valid}" ]; then
	return 3
    fi
    if [ $v1 -eq $v2 ]; then
	return 0
    elif [ $v1 -gt $v2 ]; then
	return 1
    else
	return 2
    fi
}

#------------------------------------------------------------------------------
# cacao_is_install_configured
#
# DESCRIPTION :
# tells if cacao as configured (check presence of  the configured file)
# 
# PARAMETERS :
# none
# 
# RETURN CODE: 
# CACAO_TRUE
# CACAO_FALSE
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_is_install_configured() {

    if [ ! -f "${cacao_configured_file}" ]
    then
	return  ${CACAO_FALSE}
    fi

    
    new_installed_version_str=`cacao_get_version_from_file "${cacao_template_config_dir}/private/cacao.properties"`
    old_configured_version_str=`${CAT} ${cacao_configured_file}`
    
    # Same (non-empty) revs do nothing
    if [ -n "${old_configured_version_str}" ] && [ "${old_configured_version_str}" = "${new_installed_version_str}" ]
    then
	return ${CACAO_TRUE}
    fi

    old_configured_version=`cacao_parse_version "${old_configured_version_str}"`
    new_installed_version=`cacao_parse_version "${new_installed_version_str}"`
    # Handle the empty file case
    if [ "${old_configured_version}" = ".." ]
    then
	# Refer back to default instance as reference version
        old_configured_version_str=`cacao_get_version_from_file "${cacao_etc_instances_dir}/${CACAO_DEFAULT_INSTANCE_NAME}/private/cacao.properties"`
	old_configured_version=`cacao_parse_version "${old_configured_version_str}"`
	cacao_print_syslog_notice_message "Upgrading cacao from ${old_configured_version} to ${new_installed_version}"

	return ${CACAO_FALSE}
    fi

    # Major rev compare
    i_maj=`${ECHO} ${new_installed_version} | ${AWK} -F. '{print $1}'`
    o_maj=`${ECHO} ${old_configured_version} | ${AWK} -F. '{print $1}'`
    cacao_check_if_lower "${i_maj}" "${o_maj}"
    ret=$?

    # Invalid rev string
    if [ $ret -eq 3 ]
    then
	cacao_print_error_message "${CACAO_MSG_ERROR_CC_PROP_VALUE}" "${CACAO_VERSION_KEY}"
	return ${CACAO_CR_ERROR}
    fi

	# Newly installed is greater than former configured
    if [ $ret -eq 1 ]
    then
	cacao_print_syslog_notice_message "Upgrading cacao from ${old_configured_version} to ${new_installed_version}"
	return ${CACAO_FALSE}
    fi

    # TODO: Downgrading case not differentiated here

    # Minor rev compare
    i_min=`${ECHO} ${new_installed_version} | ${AWK} -F. '{print $2}'`
    o_min=`${ECHO} ${old_configured_version} | ${AWK} -F. '{print $2}'`
    cacao_check_if_lower "${i_min}" "${o_min}"
    ret=$?

    # Invalid rev string
    if [ $ret -eq 3 ]
    then
	cacao_print_error_message "${CACAO_MSG_ERROR_CC_PROP_VALUE}" "${CACAO_VERSION_KEY}"
	return ${CACAO_CR_ERROR}
    fi

	# Newly installed is greater than former configured
    if [ $ret -eq 1 ]
    then
	cacao_print_syslog_notice_message "Upgrading cacao from ${old_configured_version} to ${new_installed_version}"
	return ${CACAO_FALSE}
    fi

    # TODO: Downgrading case not differentiated here

    # Sub rev compare
    # Just to cope with former rev numbers including dots we use awk
    i_sub=`${ECHO} ${new_installed_version} | ${CUT} -d. -f3- | ${AWK} '{ver=$0 ; gsub(/[^0-9]/,"",ver); print substr(ver*10000,0,5)}'`
    o_sub=`${ECHO} ${old_configured_version} | ${CUT} -d. -f3- | ${AWK} '{ver=$0 ; gsub(/[^0-9]/,"",ver); print substr(ver*10000,0,5)}'`
    cacao_check_if_lower "${i_sub}" "${o_sub}"
    ret=$?

    # Invalid rev string
    if [ $ret -eq 3 ]
    then
	cacao_print_error_message "${CACAO_MSG_ERROR_CC_PROP_VALUE}" "${CACAO_VERSION_KEY}"
	return ${CACAO_CR_ERROR}
    fi

    # Newly installed is greater than former configured
    if [ $ret -eq 1 ]; then
	cacao_print_syslog_notice_message "Upgrading cacao from ${old_configured_version} to ${new_installed_version}"
	return ${CACAO_FALSE}
    fi

    # TODO: Downgrading case not differentiated here

    return ${CACAO_TRUE}
   
}

#------------------------------------------------------------------------------
# cacao_add_config
#
# DESCRIPTION :
# add a property into cacao.properties with its template's value
# if it doesn't exist already. If it exists, leave it as-is
# 
# PARAMETERS :
# $1: property key
# $2: instance name
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_add_config() {

    _key="$1"
    _i="$2"
    _file="${cacao_etc_instances_dir}/${_i}/private/cacao.properties"

    _old_value="`cacao_get_property ${_key} ${_file}`"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
	# Add the property if it wasn't there already and put an empty string as value
        cacao_add_property_to_file "${_file}" "${_key}" ""
        if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
        then
            return ${CACAO_CR_ERROR}
        fi
	# Now we can update the empty value put earlier on to the default template one
        cacao_update_config "${_key}" "${_i}"
        if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
        then
            return ${CACAO_CR_ERROR}
        fi
    fi
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_update_config
#
# DESCRIPTION :
# update a property from cacao.properties with its template's value
# 
# PARAMETERS :
# $1: property key
# $2: instance name
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_update_config() {

    _key="$1"
    _i="$2"
    _file="${cacao_etc_instances_dir}/${_i}/private/cacao.properties"
    _template="${cacao_template_config_dir}/private/cacao.properties"

    _old_value="`cacao_get_property ${_key} ${_file}`"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        return ${CACAO_CR_ERROR}
    fi

    _new_value="`cacao_get_property ${_key} ${_template}`"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
       return ${CACAO_CR_ERROR}
    fi

    if [ -z "${_new_value}" ] && [ -n "${_old_value}" ]
    then
        return ${CACAO_CR_ERROR}
    fi

    if [ "${_old_value}" != "${_new_value}" ]
    then
        cacao_set_property_to_file "${_file}" "${_key}" "${_new_value}"
        if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
        then
            return ${CACAO_CR_ERROR}
        fi
        cacao_print_syslog_notice_message "${NOTICE_UPDATED_CONF}" "${_i}" \
            "${_key}" "${_old_value}" "${_new_value}"
    fi
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_remove_java_flag
#
# DESCRIPTION :
# remove a java flag inside cacao.properties:
# - remove -Xms4M
# See defect 6921997
#
# PARAMETERS :
# $1: Cacao instance name
# $2: property key
# $3: flag name without dash, like Xms4M for -Xms4M
#
# RETURN CODE:
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
#
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_remove_java_flag() {

    _instance="${1}"
    _key="${2}"
    _pattern="${3}"
    _flag="-${3}"

    _file="${cacao_etc_instances_dir}/${_instance}/private/cacao.properties"
    _old_value="`cacao_get_property ${_key} ${_file}`"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        return ${CACAO_CR_ERROR}
    fi

    # Don't remove if flag not specified
    ${ECHO} "${_old_value}" | ${GREP} "${_pattern}" >/dev/null 2>&1
    if [ ${?} -ne 0 ]
    then
        return ${CACAO_CR_SUCCESS}
    fi

    # Remove flag
    _new_value="`${ECHO} ${_old_value} | ${SED} s/${_flag}//`"
    cacao_set_property_to_file "${_file}" "${_key}" "${_new_value}"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        return ${CACAO_CR_ERROR}
    fi
    cacao_print_syslog_notice_message "${NOTICE_UPDATED_CONF}" "${_instance}" \
        "${_key}" "${_old_value}" "${_new_value}"
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_update_java_flags
#
# DESCRIPTION :
# modify a java flag inside cacao.properties:
# - add -Dfile.encoding=utf-8 to java.flags if -Dfile.encoding= not already set
# - add -Dcom.sun.cacao.debug to java.debug.flags if not already set
# - add -Djava.endorsed.dirs=<CACAO_DIR>/lib/endorsed
# See defects 6422422, 6461406
#
# PARAMETERS :
# $1: Cacao instance name
# $2: property key
# $3: flag name, like file.encoding or com.sun.cacao.debug
# $4: optional flag value, like utf-8 for file.encoding=utf-8
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_update_java_flags() {

    _instance="${1}"
    _key="${2}"
    if [ $# -eq 4 ]; then
        # Example: -Dfile.encoding=utf-8
        _pattern="\-D${3}="
        _flag="-D${3}=${4}"
    else
        # Example: -Dcom.sun.cacao.debug
        _pattern="\-D${3}"
        _flag="-D${3}"
    fi

    _file="${cacao_etc_instances_dir}/${_instance}/private/cacao.properties"
    _old_value="`cacao_get_property ${_key} ${_file}`"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        return ${CACAO_CR_ERROR}
    fi

    # Don't duplicate if flag already set
    ${ECHO} "${_old_value}" | ${GREP} "${_pattern}" >/dev/null 2>&1
    if [ ${?} -eq 0 ]
    then
        return ${CACAO_CR_SUCCESS}
    fi

    # Append flag
    _new_value="${_old_value} ${_flag}"
    cacao_set_property_to_file "${_file}" "${_key}" "${_new_value}"
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        return ${CACAO_CR_ERROR}
    fi
    cacao_print_syslog_notice_message "${NOTICE_UPDATED_CONF}" "${_instance}" \
        "${_key}" "${_old_value}" "${_new_value}"
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_do_sys_config
#
# DESCRIPTION :
# create the default core instances if needed.
# sys config all the startup management when unconfigured (.configured file
# not present) and mark it as configured (.config file present). Implementation
# function
# 
# PARAMETERS :
# 1 if called from within upgrade mechanism else 0
# 
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR 
#
# OUTPUT:
# none
#------------------------------------------------------------------------------
cacao_do_sys_config() {

    # take admin lock
    cacao_lock ${cacao_admin_lock_file}
    lock_rc=$?
    if [ ${lock_rc} -ne ${CACAO_CR_SUCCESS} ]
    then
	cacao_print_error_message "${CACAO_LOCK}"
	cacao_print_error_message "${CACAO_LOCK2}" "${cacao_admin_lock_file}"
	return ${CACAO_CR_ERROR}
    fi  

    # migrate already existing instances if any
    _instances_list="`${LS} -1 ${cacao_etc_instances_dir} 2>/dev/null`"
    if [ ${?} -eq 0 ] && [ -n "${_instances_list}" ]
    then
        for _i in ${_instances_list}
        do

            # Do nothing if properties file doesn't exist
            _file="${cacao_etc_instances_dir}/${_i}/private/cacao.properties"
            if [ ! -f "${_file}" ]
            then
                continue
            fi
            
            # Update Cacao version
            cacao_update_config "${CACAO_VERSION_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Update Cacao compatibility list
            cacao_update_config "${CACAO_COMPATIBILITY_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao micro agent property if not already specified
            cacao_add_config "${CACAO_MICRO_AGENT}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao heartbeat tm property if not already specified
            cacao_add_config "${CACAO_WATCHDOG_HB_TM_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi
            
            # Add Cacao probe frequency property if not already specified
            cacao_add_config "${CACAO_WATCHDOG_PROBE_FREQ_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi
	    
            # Add Cacao webserver.want.client.auth property if not already specified
            cacao_add_config "${CACAO_WEBSERVER_WANT_CLIENT_AUTH}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao shared libs property if not already specified
            cacao_add_config "${CACAO_SHARED_LIBS_PATH_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao connectors reuse address property if not already specified
            cacao_add_config "${CACAO_CONNECTORS_REUSE_ADDRESS_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao java flags if not already specified
            cacao_update_java_flags "${_i}" "${CACAO_JAVA_FLAGS_KEY}" \
                "file.encoding" "utf-8"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Update endorsed dir java flags if not already specified
            cacao_update_java_flags "${_i}" "${CACAO_JAVA_FLAGS_KEY}" \
                "java.endorsed.dirs" "${cacao_rt_dir}/lib/endorsed"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Remove minimum heap size if specified
            cacao_remove_java_flag "${_i}" "${CACAO_JAVA_FLAGS_KEY}" "Xms4M"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao java flags if not already specified
            cacao_update_java_flags "${_i}" "${CACAO_JAVA_DEBUG_FLAGS_KEY}" \
                "com.sun.cacao.debug"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi

            # Add Cacao java env vars property if not already specified
            cacao_add_config "${CACAO_JAVA_ENV_VARS_KEY}" "${_i}" ""
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi
	    
            # Add excluded cipher suites property if not already specified
            cacao_add_config "${CACAO_EXCLUDED_CIPHER_SUITES_KEY}" "${_i}"
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                return ${CACAO_CR_ERROR}
            fi
        done
    fi

    # create the default instances
    cacao_create_core_instances ${cacao_etc_instances_dir}
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        return ${CACAO_CR_ERROR}
    fi
    
    
    #trust what we can find in conf file
    cacao_init_unique_name_from_property
    if [ $? -ne ${CACAO_CR_SUCCESS} ] || [ -z "${cacao_unique_name}" ]
    then
	#compute the name ourself
	cacao_unique_name="`cacao_compute_unique_name`"
	if [ $? -ne ${CACAO_CR_SUCCESS} ]
	then
            return ${CACAO_CR_ERROR} 
	fi
    fi
    

    # if we are in non-root install mode
    # do not try install startup config
    cacao_is_startup_action_allowed
    if [ $? -eq ${CACAO_TRUE} ]
    then

        # configure startup for the instances
	cacao_create_instance_startup
	if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
        then
            # Rollback
	    cacao_delete_startup
	    return ${CACAO_CR_ERROR} 
	fi
    fi

    
    cacao_add_system_hooks
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
	return ${CACAO_CR_ERROR}
    fi

    # Store the install id
    cacao_create_install_properties_file
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
        cacao_delete_startup
        return ${CACAO_CR_ERROR}
    fi

    cacao_mark_as_configured

    #unlock
    cacao_unlock
    
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_create_install_properties_file
#
# DESCRIPTION :
# Create an install properties file and write into it an install id
# 
# PARAMETERS :
# None
#
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR 
#
# OUTPUT:
# None
#------------------------------------------------------------------------------
cacao_create_install_properties_file() {

    ${TOUCH} ${cacao_install_properties_file} 2>/dev/null
    if [ ${?} -ne 0 ]
    then
        cacao_print_error_message "${CACAO_MSG_ERROR_FILE_TOUCH}" ${cacao_install_properties_file}
        return ${CACAO_CR_ERROR}
    fi
    ${ECHO} "${CACAO_INSTALL_ID_KEY}=${cacao_unique_name}" > ${cacao_install_properties_file} 2>/dev/null
    if [ ${?} -ne 0 ]
    then
        return ${CACAO_CR_ERROR}
    fi
    return ${CACAO_CR_SUCCESS}
}

#------------------------------------------------------------------------------
# cacao_do_sys_unconfig
#
# DESCRIPTION :
# stop all the instances and 
# unsys config all the startup management  and mark it as not configured 
# (.config file removed). Implementation function
# 
# PARAMETERS :
# None
# 
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR 
#
# OUTPUT:
# none
#------------------------------------------------------------------------------
cacao_do_sys_unconfig() {

    # take admin lock
    cacao_lock ${cacao_admin_lock_file}
    lock_rc=$?
    if [ ${lock_rc} -ne ${CACAO_CR_SUCCESS} ]
    then
	cacao_print_error_message "${CACAO_LOCK}"
	cacao_print_error_message "${CACAO_LOCK2}" "${cacao_admin_lock_file}"
	cacao_exit ${lock_cr}
    fi  
   
    #stop the instances
    cr_res=${CACAO_CR_SUCCESS}
    instances="`${LS} -1 ${cacao_etc_instances_dir} 2>/dev/null`"
    if [ ${?} -ne 0 ]
    then
        cr_res=${CACAO_CR_ERROR}
    fi
    for i in ${instances}
    do
        cacao_is_embedded_instance ${i}
        # don't stop embedded stuff
        if [ ${?} -eq ${CACAO_FALSE} ]
        then
            ${cacao_rt_dir}/bin/cacaoadm stop -i ${i}
            if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
            then
                cr_res=${CACAO_CR_ERROR}
            fi
	    _svc_file="${cacao_etc_instances_dir}/${i}/private/${CACAO_SMF_SVC_MANIFEST_FILE_NAME}"
	    if [ -n "$_svc_file" ] && [ -f "$_svc_file" ]
	    then
		${RM} -f ${_svc_file} 2>/dev/null
	    fi
        fi
    done
    
    # if we are in non-root install mode
    # do not try to remove startup config
    cacao_is_startup_action_allowed
    if [ $? -eq ${CACAO_TRUE} ]
    then
        # delete the startup stuff
	cacao_delete_startup
	if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
	then
	    cr_res=${CACAO_CR_ERROR}
	fi
    fi

    cacao_remove_system_hooks
    if [ ${?} -ne ${CACAO_CR_SUCCESS} ]
    then
	return ${CACAO_CR_ERROR}
    fi

    # Clear install id property (even in case of error)
    ${RM} -f ${cacao_install_properties_file} 2>/dev/null
    if [ $? -ne 0 ]
    then
        cr_res=${CACAO_CR_ERROR} 
    fi
    
    # set unconfigured state (even in case of error for the moment)
    cacao_mark_as_unconfigured
  
    cacao_unlock

    return ${cr_res}
}

#------------------------------------------------------------------------------
# cacao_create_core_instances
#
# DESCRIPTION :
# create core defaults instances
# looks for ${cacao_tools_dir}/instance_definition_xx.cfg files
# and creates associated instances.
#
# PARAMETERS :
# none
# 
# RETURN CODE: 
# CACAO_CR_SUCCESS
# CACAO_CR_ERROR
# 
# OUTPUT:
# None.
#------------------------------------------------------------------------------
cacao_create_core_instances() {

    _final_rc=${CACAO_CR_SUCCESS}

    for inst_cfg in ${cacao_tools_dir}/instance_definition_*.cfg
    do
      instance_name=`${BASENAME} ${inst_cfg} .cfg | ${CUT} -s -d_ -f3`
      if [ -n "${instance_name}" ]
      then
	  cacao_is_instance_exists "${instance_name}"
	  if [ ${?} -eq ${CACAO_FALSE} ]
	  then
            cacao_do_create_instance ${instance_name} ${CACAO_FALSE_VALUE}
             _final_rc=$?
            if [ ${_final_rc} -ne ${CACAO_CR_SUCCESS} ]
            then
	      #even if error, go on for others core ones
	      cacao_print_error_message "${CACAO_MSG_ERROR_INSTANCE_CORE_INSTALL}" \
                                        "${instance_name}"
            fi
          fi
      fi
    done
    
    return ${_final_rc}
}


