#!/bin/sh ############################################################################# # # MCAFEE CONFIDENTIAL # Copyright ©2018 McAfee, LLC # # The source code contained or described herein and all documents related # to the source code ("Material") are owned by McAfee or its # suppliers or licensors. Title to the Material remains with McAfee # or its suppliers and licensors. The Material contains trade # secrets and proprietary and confidential information of McAfee or its # suppliers and licensors. The Material is protected by worldwide copyright # and trade secret laws and treaty provisions. No part of the Material may # be used, copied, reproduced, modified, published, uploaded, posted, # transmitted, distributed, or disclosed in any way without McAfee's prior # express written permission. # # No license under any patent, copyright, trade secret or other intellectual # property right is granted to or conferred upon you by disclosure or # delivery of the Materials, either expressly, by implication, inducement, # estoppel or otherwise. Any license under such intellectual property rights # must be express and approved by McAfee in writing. # ############################################################################## # # Used for matching the version . /etc/shgw/shgw.version # # Load all the variables . /etc/shgw/shgw.constants . /etc/shgw/shgw.common . /etc/shgw/shgw.env . /etc/shgw/shgw.errno . /etc/shgw/shgw_migrate fn_trim_startup_log ${SHGW_LOG_TRIMMER} & # # Enable deep inspection debugging of this shell script exec 3>&1 4>&2 1>> ${SHGW_STARTUP_LOG} 2>&1 set -x fn_retry_cmd_upto_five_times() { local _cmd=$1 local _ecode=$2 COUNT=1 while [ $COUNT -lt $SQL_FAILURE_RETRY_COUNT ]; do eval $_cmd > /dev/null 2>&1 if [ $? -eq 0 ]; then break fi sleep 1 COUNT=$((${COUNT} + 1)) done if [ $COUNT -eq $SQL_FAILURE_RETRY_COUNT ]; then fn_err_exit $_ecode fi } create_debug_files(){ if [ ! -f ${SHGW_STARTUP_STATUS} ]; then > ${SHGW_STARTUP_STATUS} fi if [ ! -f ${SHGW_ERROR_FILE} ]; then > ${SHGW_ERROR_FILE} fi } get_lan_ifaces() { local _IFACE="" LAN_INTERFACE_JSON_LIST="" for _IFACE in ${LAN_INTERFACES}; do if [ ! -z ${LAN_INTERFACE_JSON_LIST} ]; then LAN_INTERFACE_JSON_LIST=${LAN_INTERFACE_JSON_LIST}',' fi LAN_INTERFACE_JSON_LIST=${LAN_INTERFACE_JSON_LIST}'"'${_IFACE}'"' done if [ -z ${LAN_INTERFACE_JSON_LIST} ]; then fn_err_exit ${NO_LAN_IFACE} fi LAN_INTERFACE_JSON_LIST='['${LAN_INTERFACE_JSON_LIST}']' ${ECHO} "[$(fn_time_now)] LAN_INTERFACES = ${LAN_INTERFACE_JSON_LIST} " >> ${SHGW_STARTUP_STATUS} } create_persistant_sqlite_db(){ ${SHGW_ENCRYPT_SQL} "START" "PERSIST" } update_persistant_sqlite_db() { if [ X"$mode" == X"softstart" ]; then reset=0 ${SHGW_ENCRYPT_SQL} "UPDATE_START" "${LAN_INTERFACE_JSON_LIST}" "${SHGW_VERSION}" "${IP_SKIP_JSON_LIST}" "${base_mac}" "${serial}" "${model}" "${country_code}" "${timezone}" "${WAN_INTERFACE_JSON_LIST}" "${DEFAULT_WAN_INTERFACE}" "${DEFAULT_DNS_SERVER_LIST}" "${LAN_IP_LIST}" "${LAN_IFACE_IP_LIST}" "${reset}" elif [ X"$mode" == X"db_start" ]; then reset=2 ${SHGW_ENCRYPT_SQL} "UPDATE_START" "${LAN_INTERFACE_JSON_LIST}" "${SHGW_VERSION}" "${IP_SKIP_JSON_LIST}" "${base_mac}" "${serial}" "${model}" "${country_code}" "${timezone}" "${WAN_INTERFACE_JSON_LIST}" "${DEFAULT_WAN_INTERFACE}" "${DEFAULT_DNS_SERVER_LIST}" "${LAN_IP_LIST}" "${LAN_IFACE_IP_LIST}" "${reset}" else ${SHGW_ENCRYPT_SQL} "UPDATE_START" "${LAN_INTERFACE_JSON_LIST}" "${SHGW_VERSION}" "${IP_SKIP_JSON_LIST}" "${base_mac}" "${serial}" "${model}" "${country_code}" "${timezone}" "${WAN_INTERFACE_JSON_LIST}" "${DEFAULT_WAN_INTERFACE}" "${DEFAULT_DNS_SERVER_LIST}" "${LAN_IP_LIST}" "${LAN_IFACE_IP_LIST}" fi } check_persistant_db(){ local _need_to_create_db=0 if [ -f ${SHGW_PERSISTANT_DB} ]; then local _shgw_version_from_sql=$(${SHGW_ENCRYPT_SQL} "GET" "VERSION" "shgw_config_store") if [ "${_shgw_version_from_sql}" != "${SHGW_VERSION}" ]; then fn_migrate_persistant_db fi else # persistant db not found _need_to_create_db=1 fi if [ ${_need_to_create_db} -eq 1 ]; then create_persistant_sqlite_db fi } fetch_skip_ips() { if [ ! -f ${IP_SKIP_LIST_FILE} ]; then ${ECHO} "[$(fn_time_now)] No Skip IPs file" >> ${SHGW_STARTUP_STATUS} IP_SKIP_JSON_LIST='[""]' else IP_SKIP_JSON_LIST="" while read line do if [ ! -z ${IP_SKIP_JSON_LIST} ]; then IP_SKIP_JSON_LIST=${IP_SKIP_JSON_LIST}',' fi IP_SKIP_JSON_LIST=${IP_SKIP_JSON_LIST}'"'${line}'"' done < ${IP_SKIP_LIST_FILE} if [ -z ${IP_SKIP_JSON_LIST} ]; then ${ECHO} "[$(fn_time_now)] No Skip IPs" >> ${SHGW_STARTUP_STATUS} fi IP_SKIP_JSON_LIST='['${IP_SKIP_JSON_LIST}']' ${ECHO} "[$(fn_time_now)] Skipping IPs = ${IP_SKIP_JSON_LIST} " >> ${SHGW_STARTUP_STATUS} fi } __fetch_wan_and_dns_data() { local line=${1} local wan="" local dns="" local res="" wan=$(${ECHO} ${line} | ${CUT} -d';' -f1) dns=$(${ECHO} ${line} | ${CUT} -d';' -f2 | ${SED} 's/,/ /g') dns_list="" if [ ! -z "${dns}" ]; then for i in ${dns}; do if [ ! -z ${dns_list} ]; then dns_list=${dns_list}',' fi dns_list=${dns_list}'"'${i}'"' done res='{"interface":"'${wan}'","dns":['${dns_list}']}' fi ${ECHO} $res } fetch_wan_interfaces() { DEFAULT_WAN_INTERFACE="" WAN_INTERFACE_JSON_LIST='' if [ ! -f ${WAN_INFO} ]; then ${ECHO} "[$(fn_time_now)] No WAN Info file" >> ${SHGW_STARTUP_STATUS} fn_err_exit ${NO_DEFAULT_WAN_IFACE} else while read line do if [ ! -z "$(${ECHO} ${line} | ${GREP} default)" ]; then DEFAULT_WAN_INTERFACE=$(${ECHO} ${line} | ${AWK} '{print $2}') else dns_list="" dns_list=$(__fetch_wan_and_dns_data ${line}) #fetch default DNS server CUR_WAN_INTERFACE=$(${ECHO} ${dns_list} | ${CUT} -d':' -f2 | ${CUT} -d',' -f1 | ${SED} -e 's/"//g') if [ X"$CUR_WAN_INTERFACE" = X"$DEFAULT_WAN_INTERFACE" ]; then DEFAULT_DNS_SERVER_LIST=$(${ECHO} ${dns_list} | ${CUT} -d'[' -f2 | ${SED} -e 's/"//g' -e 's/]//g' -e 's/}//g') fi if [ ! -z ${dns_list} ]; then if [ ! -z ${WAN_INTERFACE_JSON_LIST} ]; then WAN_INTERFACE_JSON_LIST=${WAN_INTERFACE_JSON_LIST}',' fi WAN_INTERFACE_JSON_LIST=${WAN_INTERFACE_JSON_LIST}${dns_list} fi fi done < ${WAN_INFO} fi if [ -z ${DEFAULT_WAN_INTERFACE} ]; then ${ECHO} "[$(fn_time_now)] No Default WAN Interface" >> ${SHGW_STARTUP_STATUS} fn_err_exit ${NO_DEFAULT_WAN_IFACE} fi # exit if there is no default DNS server if [ -z ${DEFAULT_DNS_SERVER_LIST} ]; then ${ECHO} "[$(fn_time_now)] No Default DNS Server" >> ${SHGW_STARTUP_STATUS} fn_err_exit ${NO_DEFAULT_DNS_SERVER_LIST} fi if [ -z ${WAN_INTERFACE_JSON_LIST} ]; then ${ECHO} "[$(fn_time_now)] No WAN Interfaces" >> ${SHGW_STARTUP_STATUS} fn_err_exit ${NO_DEFAULT_WAN_IFACE} fi WAN_INTERFACE_JSON_LIST="["${WAN_INTERFACE_JSON_LIST}"]" ${ECHO} "[$(fn_time_now)] Default WAN Interfaces: ${DEFAULT_WAN_INTERFACE}" >> ${SHGW_STARTUP_STATUS} ${ECHO} "[$(fn_time_now)] Default DNS server list: ${DEFAULT_DNS_SERVER_LIST}" >> ${SHGW_STARTUP_STATUS} ${ECHO} "[$(fn_time_now)] WAN Interfaces: ${WAN_INTERFACE_JSON_LIST}" >> ${SHGW_STARTUP_STATUS} } __fetch_lan_and_ip_data() { local line=${1} local lan="" local ip="" local res="" lan=$(${ECHO} ${line} | ${CUT} -d';' -f1) ip=$(${ECHO} ${line} | ${CUT} -d';' -f2 | ${SED} 's/,/ /g') ip_list="" if [ ! -z "${ip}" ]; then for i in ${ip}; do if [ ! -z ${ip_list} ]; then ip_list=${ip_list}',' fi ip_list=${ip_list}'"'${i}'"' done res='{"interface":"'${lan}'","lan_ip":['${ip_list}']}' fi ${ECHO} $res } fetch_lan_ip() { local line=${1} local ip="" ip=$(${ECHO} ${line} | ${CUT} -d';' -f2 | ${SED} 's/,/ /g') if [ ! -z "${ip}" ]; then for i in ${ip}; do if [ ! -z "$LAN_IP_LIST" ]; then LAN_IP_LIST=${LAN_IP_LIST}',' fi LAN_IP_LIST=${LAN_IP_LIST}'"'${i}'"' done else LAN_IP_LIST='"192.168.1.1"' fi ${ECHO} ${LAN_IP_LIST} } fetch_lan_interfaces() { LAN_INTERFACES="" LAN_IP_LIST="" LAN_IFACE_IP_LIST="" local lan="" if [ ! -f ${LAN_INFO} ]; then ${ECHO} "[$(fn_time_now)] No LAN Info file" >> ${SHGW_STARTUP_STATUS} LAN_INTERFACES="br0" LAN_IP_LIST='"192.168.1.1"' else while read line do if [ ! -z "$LAN_INTERFACES" ]; then LAN_INTERFACES=${LAN_INTERFACES}' ' fi lan=$(${ECHO} ${line} | ${CUT} -d';' -f1) LAN_INTERFACES=${LAN_INTERFACES}${lan} if [ ! -z "$(${ECHO} ${line} | ${GREP} br0)" ]; then LAN_IP_LIST=$(fetch_lan_ip ${line}) fi ip_list="" ip_list=$(__fetch_lan_and_ip_data ${line}) if [ ! -z ${ip_list} ]; then if [ ! -z ${LAN_IFACE_IP_LIST} ]; then LAN_IFACE_IP_LIST=${LAN_IFACE_IP_LIST}',' fi LAN_IFACE_IP_LIST=${LAN_IFACE_IP_LIST}${ip_list} fi done < ${LAN_INFO} fi LAN_IP_LIST='['${LAN_IP_LIST}']' LAN_IFACE_IP_LIST='['${LAN_IFACE_IP_LIST}']' ${ECHO} "[$(fn_time_now)] LAN Interfaces: ${LAN_INTERFACES}" >> ${SHGW_STARTUP_STATUS} ${ECHO} "[$(fn_time_now)] LAN IP for br0: ${LAN_IP_LIST}" >> ${SHGW_STARTUP_STATUS} ${ECHO} "[$(fn_time_now)] LAN IP for all interfcaes: ${LAN_IFACE_IP_LIST}" >> ${SHGW_STARTUP_STATUS} } fetch_and_update_gwinfo() { if [ ! -f ${HGUINFO} ]; then ${ECHO} "[$(fn_time_now)] No HGU Info file" >> ${SHGW_STARTUP_STATUS} fn_err_exit ${FETCH_BASE_MAC_FAILED} else serial=$(${ECHO} $(${CUT} -d ';' -f1 ${HGUINFO})) model=$(${ECHO} $(${CUT} -d ';' -f2 ${HGUINFO})) timezone=$(${ECHO} $(${CUT} -d ';' -f3 ${HGUINFO})) country_code=$(${ECHO} $(${CUT} -d ';' -f4 ${HGUINFO})) base_mac=$(${ECHO} $(${CUT} -d ';' -f5 ${HGUINFO})) fi if [ -z "${base_mac}" ]; then fn_err_exit ${FETCH_BASE_MAC_FAILED} fi if [ -z ${serial} ]; then ${ECHO} "[$(fn_time_now)] Serial number is empty!" serial="serial" fi if [ -z ${model} ]; then ${ECHO} "[$(fn_time_now)] Model number is empty!" model="model" fi if [ -z ${country_code} ]; then ${ECHO} "[$(fn_time_now)] Country code is empty!" country_code="ES" #Should we quit instead of this? fi # Timezone in Econet is a huge string need to understand timezone="" if [ -z ${timezone} ]; then ${ECHO} "[$(fn_time_now)] Timezone is empty!" timezone="GMT" fi if [ -z ${tproxy_mark} ]; then ${ECHO} "[$(fn_time_now)] tproxy_mark is empty!" tproxy_mark="0x4000" fi if [ -z ${tproxy_mask} ]; then ${ECHO} "[$(fn_time_now)] tproxy_mask is empty!" tproxy_mask="0x4000" fi } create_non_persistant_sqlite_db(){ fn_retry_query_upto_five_times "CREATE TABLE IF NOT EXISTS device_discovery_table(dev_id TEXT PRIMARY KEY, mac TEXT,ip_address TEXT,ip6_address TEXT,host_name TEXT,headless INTEGER,status INTEGER,last_seen INTEGER,trusted INTEGER);" "${SHGW_NON_PERSISTANT_DB}" "${NON_PERSISTANT_DB_UPDATE_FAILED}" "${ONE_SEC}" fn_retry_query_upto_five_times "CREATE TABLE IF NOT EXISTS stats(key TEXT PRIMARY KEY, value TEXT);" "${SHGW_NON_PERSISTANT_DB}" "${NON_PERSISTANT_DB_UPDATE_FAILED}" "${ONE_SEC}" fn_retry_query_upto_five_times "DELETE FROM stats;" "${SHGW_NON_PERSISTANT_DB}" "${NON_PERSISTANT_DB_UPDATE_FAILED}" "${ONE_SEC}" fn_retry_query_upto_five_times "INSERT INTO stats VALUES('dns_stats', '{}');" "${SHGW_NON_PERSISTANT_DB}" "${NON_PERSISTANT_DB_UPDATE_FAILED}" "${ONE_SEC}" fn_retry_query_upto_five_times "INSERT INTO stats VALUES('sys_stats', '{}');" "${SHGW_NON_PERSISTANT_DB}" "${NON_PERSISTANT_DB_UPDATE_FAILED}" "${ONE_SEC}" fn_retry_query_upto_five_times "CREATE TABLE IF NOT EXISTS shgw_access_restrictions(status INTEGER, protocol TEXT, port INTEGER, source TEXT, devices TEXT);" "${SHGW_NON_PERSISTANT_DB}" "${NON_PERSISTANT_DB_UPDATE_FAILED}" "${ONE_SEC}" } delete_old_persistent_db() { if [ -f ${SHGW_OLD_PERSISTANT_DB} ]; then ${RM} -f ${SHGW_OLD_PERSISTANT_DB} fi } #------------------------------------start_server------------------------------ start_watchdogd() { #Remove the o/p redirection done by exec exec 1>&3 2>&4 ${SHGW_WD_MONIT} & #Add the o/p redirection exec 3>&1 4>&2 1>> ${SHGW_STARTUP_LOG} 2>&1 wd_pid=$(${PS} | ${GREP} -i "shgw_watchdogd" | ${GREP} -v "grep" | ${AWK} -v OFS=' ' '{print $1}') if [ ! -z $wd_pid ]; then # request start ${KILL} -SIGUSR2 $wd_pid fi } create_shgw_directories() { ${MKDIR} -p ${SHGW_NVRAM} ${MKDIR} -p ${SHGW_TMPFS_PATH} } check_tld_json_existence() { if [ ! -f ${TLD_JSON_FILE} ];then ${CP} ${SHGW_PRIVATE}/shgw_tld_file.json ${SHGW_NVRAM} ${CHMOD} 666 ${TLD_JSON_FILE} fi } set_time() { rtm_util cfg igd time_ntp set 1 adm_state enable ip_intf 2 ntp_svr_1 211.22.103.157 } #------------------------------------>MAIN<---------------------------------------- start_shg(){ delete_old_persistent_db create_shgw_directories fetch_wan_interfaces fetch_lan_interfaces get_lan_ifaces check_persistant_db fetch_and_update_gwinfo #calc_gwinfo fetch_skip_ips update_persistant_sqlite_db #set_time ${SHGW_ACCESS_RESTRICTION} "inbound_sec_start" create_non_persistant_sqlite_db ${ECHO} "[$(fn_time_now)] Database created successfully" >> ${SHGW_STARTUP_STATUS} check_tld_json_existence start_watchdogd } force_start_shg() { ${SHGW_ENCRYPT_SQL} "UPDATE" "STOP_STATUS" "0" start_shg } stop_shg(){ ${SHGW_ACCESS_RESTRICTION} "inbound_sec_stop" # request stop wd_pid=$(ps | ${GREP} -i "shgw_watchdogd" | ${GREP} -v "grep" | ${AWK} -v OFS=' ' '{print $1}') if [ ! -z $wd_pid ]; then # request stop ${KILL} -SIGUSR1 $wd_pid fi } force_stop_shg(){ ${SHGW_ENCRYPT_SQL} "UPDATE" "STOP_STATUS" "1" stop_shg } kill_shg() { ${ECHO} "Killing SHGW" stop_shg wd_monit_pid=$(${PS} | ${GREP} -i "shgw_wd_monit" | ${GREP} -v "grep" | ${AWK} -v OFS=' ' '{print $1}') if [ ! -z $wd_monit_pid ]; then ${ECHO} "Stopping monit!" ${KILL} -9 $wd_monit_pid fi wd_pid=$(${PS} | ${GREP} -i "shgw_watchdogd" | ${GREP} -v "grep" | ${AWK} -v OFS=' ' '{print $1}') if [ ! -z $wd_pid ]; then ${ECHO} "Stopping watchdog!" ${KILL} -9 $wd_pid fi ${RM} -rf ${SHGW_TMPFS_PATH} ${RM} -rf ${SHGW_STARTUP_STATUS} ${RM} -rf ${SHGW_STARTUP_LOG} ${RM} -rf ${SHGW_ERROR_FILE} } reset_shg() { ${ECHO} "Resetting SHGW!" ${SHGW_ROUTER_RESET} hard wd_monit_pid=$(${PS} | ${GREP} -i "shgw_wd_monit" | ${GREP} -v "grep" | ${AWK} -v OFS=' ' '{print $1}') if [ ! -z $wd_monit_pid ]; then ${ECHO} "Stopping monit!" ${KILL} -9 $wd_monit_pid fi wd_pid=$(${PS} | ${GREP} -i "shgw_watchdogd" | ${GREP} -v "grep" | ${AWK} -v OFS=' ' '{print $1}') if [ ! -z $wd_pid ]; then ${ECHO} "Stopping watchdog!" ${KILL} -9 $wd_pid fi # backup ${RM} -f ${SHGW_PERSISTANT_DB} ${ECHO} "Reset done!" } shgw_mode() { if [ X"$mode" == X"start" ]; then ${ECHO} "SHGW start called!" start_shg elif [ X"$mode" == X"stop" ]; then ${ECHO} "SHGW stop called!" stop_shg elif [ X"$mode" == X"kill" ]; then ${ECHO} "SHGW kill called!" kill_shg elif [ X"$mode" == X"restart" ]; then ${ECHO} "SHGW restart called!" stop_shg sleep 3 start_shg elif [ X"$mode" == X"force_start" ]; then ${ECHO} "SHGW force_start called!" force_start_shg elif [ X"$mode" == X"force_stop" ]; then ${ECHO} "SHGW force_stop called!" force_stop_shg elif [ X"$mode" == X"reset" ]; then ${ECHO} "SHGW reset called!" reset_shg elif [ X"$mode" == X"softstart" ]; then ${ECHO} "SHGW softstart called!" start_shg elif [ X"$mode" == X"db_start" ]; then ${ECHO} "SHGW DB start called!" start_shg else ${ECHO} "Usage: $0 [start|stop|kill|restart|force_start|force_stop|reset|softstart|db_start]" fn_err_exit ${INVALID_MODE} fi ${RM} -rf $STARTUP_LOCK } exit_if_running() { # TODO : Add a fdlock implementaion local mypid=$$ if ! [ -f "$STARTUP_LOCK" ]; then ${ECHO} $$ > $STARTUP_LOCK return fi local pid_on_file=$(${CAT} "$STARTUP_LOCK") [ X"$pid_on_file" == X"$mypid" ] && return old_cmd_line=$(${CAT} /proc/$pid_on_file/cmdline 2>/dev/null) [ "$?" != "0" ] && ${ECHO} $$ > $STARTUP_LOCK && return ${ECHO} "$old_cmd_line" | ${GREP} "shgw" [ "$?" == "0" ] && ${ECHO} "Already running" && exit 127 ${ECHO} $$ > $STARTUP_LOCK } #-------------------------------------------------------------------------------- ${ECHO} "Called for: $1" exit_if_running create_debug_files ${ECHO} "[$(fn_time_now)] starting" >> ${SHGW_STARTUP_STATUS} mode=$1 shgw_mode ${ECHO} "[$(fn_time_now)] done" >> ${SHGW_STARTUP_STATUS}