HEX
Server: nginx/1.26.1
System: Linux iZrj9cbdvwu1cot8sjlyzlZ 5.10.134-15.al8.x86_64 #1 SMP Thu Jul 20 00:44:04 CST 2023 x86_64
User: www (1000)
PHP: 7.4.33
Disabled: passthru,exec,system,putenv,chroot,chgrp,chown,shell_exec,popen,proc_open,pcntl_exec,ini_alter,ini_restore,dl,openlog,syslog,readlink,symlink,popepassthru,pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority,imap_open,apache_setenv
Upload Files
File: //usr/bin/aliyun_init
#!/bin/bash


#################################################################
# configs
cloudinit_version=0.1
cloudinit_name='aliyun_init'

cloud_cfg=/etc/aliyun_init/cloud.cfg
aliyun_cloud_cfg=/etc/cloud/cloud.cfg.d/aliyun_cloud.cfg
cloudinit_log=/var/log/aliyun_init.log
cloudinit_work_dir=/var/lib/aliyun_init
cloudinit_iids=$cloudinit_work_dir/instances
cloudinit_iid_link=$cloudinit_work_dir/instance
cloudinit_sem=$cloudinit_iid_link/sem/
cloudinit_userdata_raw=$cloudinit_iid_link/user-data.txt

my_hostname=''
my_ip=''
my_ssh_pubkey=''
my_iid=''

# defaults
cloudinit_enable=1
cloudinit_debug=0
manage_hostname=1
manage_hosts=1
manage_ssh_host_key=1
manage_ssh_pub_key=1
ssh_passwd_enable=1
lock_root_passwd_login=0
run_userdata=0
config_passwd=1
retries=60
max_timeout=1
key_retries=5
sleep_time=0.5

metaserver='http://100.100.100.200'
api_version='2016-01-01'
metadata_url=$metaserver/$api_version/meta-data
userdata_url=$metaserver/$api_version/user-data

#################################################################
# common

is_enable() { test $1 == 1; }
my_log() {
	local level=$1
	shift
	echo "[`date +%Y-%m-%d-%H-%M-%S.%N`] [$level] $@" >> $cloudinit_log
}
log_info()  { my_log "INFO"  "$@"; }
log_error() { my_log "ERROR" "$@"; }
log_debug() { is_enable $cloudinit_debug && my_log "DEBUG" "$@"; }

netmask2cidr() {
    local dst_netmask=$1
    local lookup_table=(
            255.255.255.255:32
            255.255.255.254:31
            255.255.255.252:30
            255.255.255.248:29
            255.255.255.240:28
            255.255.255.224:27
            255.255.255.192:26
            255.255.255.128:25
            255.255.255.0:24
            255.255.254.0:23
            255.255.252.0:22
            255.255.248.0:21
            255.255.240.0:20
            255.255.224.0:19
            255.255.192.0:18
            255.255.128.0:17
            255.255.0.0:16
            255.254.0.0:15
            255.252.0.0:14
            255.248.0.0:13
            255.240.0.0:12
            255.224.0.0:11
            255.192.0.0:10
            255.128.0.0:9
            255.0.0.0:8
            254.0.0.0:7
            252.0.0.0:6
            248.0.0.0:5
            240.0.0.0:4
            224.0.0.0:3
            192.0.0.0:2
            128.0.0.0:1
            0.0.0.0:0
    )
    for i in ${lookup_table[@]}; do
        if [[ $dst_netmask == ${i%%:*} ]]; then
            echo ${i##*:} # cidr
            return 0
        fi
    done
    return 1
}

lease_tmp_dir=`mktemp -d`
dhcp_lease=""
eth_ip=""
eth_routers=""
eth_mask=""
eth_cidr=""

obtain_lease_and_up_eth0() {

    cp /usr/sbin/dhclient $lease_tmp_dir

    eth0_up_cmd="ip link set dev eth0 up"
    eval $eth0_up_cmd

    dhcp_lease=$lease_tmp_dir/dhcp.lease
    dhcp_pid=$lease_tmp_dir/dhclient.pid
    lease_cmd="$lease_tmp_dir/dhclient -1 -v -lf $dhcp_lease -pf $dhcp_pid -sf /bin/true"
    eval $lease_cmd

    if [[ -f $dhcp_pid ]];then
        pid=`cat $dhcp_pid`
        if [[ -n "$pid" ]];then
            log_info "kill dhclient pid : $pid"
            kill -9 $pid
        fi
    fi

    if [[ -f $dhcp_lease ]];then
        eth_ip=`grep fixed-address $dhcp_lease |awk '{match($0,/[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+/);print substr($0,RSTART,RLENGTH)}'|grep -Ev "^127|^$"`
        eth_routers=`grep routers $dhcp_lease |awk '{match($0,/[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+/);print substr($0,RSTART,RLENGTH)}'|grep -Ev "^127|^$"`
        eth_mask=`grep subnet-mask $dhcp_lease |awk '{match($0,/[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+/);print substr($0,RSTART,RLENGTH)}'|grep -Ev "^127|^$"`
        eth_cidr=`netmask2cidr $eth_mask`

        if [[ -n "$eth_ip" ]];then
            ip_add_cmd="ip -family inet addr add $eth_ip/$eth_cidr dev eth0"
            eval $ip_add_cmd
            log_info $ip_add_cmd

            ip_link_up="ip -family inet link set dev eth0 up"
            eval $ip_link_up
            log_info $ip_link_up

            ip_route_show="ip route show 0.0.0.0/0"
            ip_route_add="ip -4 route add $eth_routers dev eth0 src $eth_ip"
            ip_default_route="ip -4 route add default via $eth_routers dev eth0"
            if [[ "X" == `${ip_route_show}`"X" ]];then
                eval $ip_route_add
                eval $ip_default_route
            fi
        fi
    fi

    return 0
}

del_lease_and_down_eth0() {
    if [[ -f $dhcp_lease ]]; then
        if [[ -n "$eth_ip" ]];then
            ip_route_default_del="ip -4 route del default  dev eth0"
            eval $ip_route_default_del
            ip_route_del="ip -4 route del $eth_routers  dev eth0"
            eval $ip_route_del
            ip_del_cmd="ip -family net addr del $eth_ip/$eth_cidr dev eth0"
            eval $ip_del_cmd
            ip_link_down="ip -family inet link  set dev eth0 down"
            eval $ip_link_down
            rm -rf $lease_tmp_dir
            log_info "del network info"
        fi
    fi
}

wait_network_ready() {
	while [[ $retries -gt 0 ]]; do
		log_info "wait_network_ready, retries $retries"
		if curl -s --fail -m $max_timeout $metaserver >& /dev/null; then
			return 0
		fi
        sleep $sleep_time
		retries=$(($retries-1))
	done
	return 1
}

prepare_env() {
	log_info "prepare_env"

	if ! which curl >& /dev/null; then
		log_error "system not install curl"
		return 1
	fi

#    if ! obtain_lease_and_up_eth0; then
#        log_error "failed to get dhcp ip info"
#        return 1
#    fi

	if ! wait_network_ready; then
		log_error "network is not ready"
		exit 1
    else
        log_info "network is ready"
	fi

	my_iid=`get_metadata_iid`
	if [[ -z $my_iid ]]; then
		log_error "failed to get instance-id"
		return 1
	fi
	log_info "instance-id: $my_iid"

	log_info "create $cloudinit_iids/$my_iid"
	mkdir -p $cloudinit_iids/$my_iid

	log_info "create symbol link $cloudinit_iid_link"
	ln -sfn  $cloudinit_iids/$my_iid $cloudinit_iid_link

	log_info "create semaphore dir $cloudinit_sem"
	mkdir -p $cloudinit_sem
}


load_config() {
	log_info "try load config file $cloud_cfg"
	source $cloud_cfg
}

is_not_run() {
	test ! -e $cloudinit_sem/$1
}

mark_run() {
	log_info "run $1"
	$1 # run it
	ret=$?
	echo $ret > $cloudinit_sem/$1
	log_info "$1 end with return code $ret"
}

try_run() {
	if is_not_run $1 ; then
		mark_run $1
	else
		log_info "$1 is already run in the previous time, skip"
	fi
}

check_and_run() {
	log_info "$2 is_enable:$1"
	is_enable $1 && try_run $2
}

my_curl() {
    every_key_retries=$key_retries
    while [[ $every_key_retries -gt 0 ]];
    do
	    cmd="curl --fail -s -m $max_timeout $1"
	    result=`$cmd`
	    log_info "$cmd, return result $result"
        if [[ -z $result ]];then
            every_key_retries=$(($every_key_retries-1))
            sleep $sleep_time
        else
            break
        fi
    done
    echo $result
}

#################################################################
# meta-server

get_metadata_iid()      { my_curl $metadata_url/instance-id; }
get_metadata_hostname() { my_curl $metadata_url/hostname; }
get_metadata_sshkey() {
    key_exist=`curl --fail -s -m $max_timeout $metadata_url/public-keys/0/`
    log_info "public-kyes: $key_exist"
    if [[ -n $key_exist ]];then
	    my_ssh_pubkey=`my_curl $metadata_url/public-keys/0/openssh-key`
    fi
	[[ -n "$my_ssh_pubkey" ]]
}


#################################################################
# configs

get_my_ip() {
	if [[ -e /sys/class/net/eth0 ]]; then
		my_ip=`ip a show dev eth0 | awk '/inet/ {print $2}' | cut -d'/' -f1`
	else
		my_ip=`my_curl $metadata_url/private-ipv4`
	fi
	[[ -n $my_ip ]]
}

get_my_hostname() {
	[[ -n $my_hostname ]] && return 0
	my_hostname=`get_metadata_hostname`
	[[ -n $my_hostname ]]
}

config_lock_root_passwd_login() {
	log_info `passwd -l root`
}

config_hostname() {
	get_my_hostname || return 1
	log_info "config_hostname: $my_hostname"

	hostnamectl set-hostname --static $my_hostname
	hostname $my_hostname
}

#only support root,encrypted
config_passwd(){
    log_info "config_passwd"
    sshd_config=/etc/ssh/sshd_config
    if [[ -L $aliyun_cloud_cfg &&  -f $aliyun_cloud_cfg ]];then
        if grep -q "^password:" $aliyun_cloud_cfg;then
            passwd=`grep -nr "^password:" $aliyun_cloud_cfg |awk '{print $NF}'`
            if [[ $passwd =~  \$(1|2a|2y|5|6)(\$.+){2} ]];then
                echo "root:$passwd" | chpasswd -e

                if grep -q -i "ssh_pwauth:[[:space:]]*true" $aliyun_cloud_cfg;then
                    sed -i '/PasswordAuthentication/d' $sshd_config
                    echo "PasswordAuthentication yes" >> $sshd_config

                fi
                log_info "success config_passwd"
                return 0

            fi
        fi
    fi
    log_info "not config_passwd"
    return 1

}

config_hosts() {
	get_my_hostname || return 1
	get_my_ip || return 1
	if [[ -e /etc/hosts ]]; then
		sed -i "/$my_hostname/d" /etc/hosts
		sed -i "/$my_ip/d" /etc/hosts
	fi

	log_info "config_hosts: $my_ip $my_hostname"
	echo "$my_ip $my_hostname $my_hostname" >> /etc/hosts
}

config_ssh_pub_key() {
	if ! get_metadata_sshkey ; then
		log_info "user not set ssh pubkey"
		return 1
	fi
	auth_file=/root/.ssh/authorized_keys
    sshd_config=/etc/ssh/sshd_config
	if [[ ! -e $auth_file ]]; then
		mkdir -p /root/.ssh/
		echo "$my_ssh_pubkey" > $auth_file
		chmod 600 $auth_file
	elif ! grep -q "$my_ssh_pubkey" $auth_file; then
		echo "$my_ssh_pubkey" >> $auth_file
	fi

    sed -i '/PasswordAuthentication/d' $sshd_config
    echo "PasswordAuthentication no" >> $sshd_config

}

# ssh host key must after hostname
config_ssh_host_key() {
	rm -f /etc/ssh/ssh_host_*_key*
	log_info `ssh-keygen -A -N ''`
}

#################################################################
# execute user-data

config_user_data() {
	if ! curl -s --fail $userdata_url -o $cloudinit_userdata_raw; then
		log_info "user not set the userdata"
		return 0
	fi

	workdir=`mktemp -d cloudinit_userdata_XXXX`
	if [[ $? != 0 ]]; then
		log_error "failed to create tempdir"
		return 1
	fi

	log_info "execute userdata in $workdir"
	( cd $workdir;
	  cp $cloudinit_userdata_raw part-00;
	  bash ./part-00;
	)
	log_info "rm -rf $workdir"
	rm -rf $workdir
}

#################################################################
# main

main() {
	if [[ $1 == 'version' || $1 == '--version' || $1 == '-v' ]]; then
		echo "$cloudinit_name $cloudinit_version"
		exit 0
	fi

	log_info "$cloudinit_name $cloudinit_version start"

	if ! load_config; then
		log_error "faild to load config file, exit"
		exit 1
	fi
	if ! is_enable $cloudinit_enable; then
		log_info "aliyun_init not enabled, exit"
		exit 1
	fi
	if ! prepare_env; then
		log_error "prepare_env failed, exit"
		exit 1
	fi

	check_and_run $manage_hostname        config_hostname
	check_and_run $manage_ssh_host_key    config_ssh_host_key
    check_and_run $manage_ssh_pub_key    config_ssh_pub_key
    check_and_run $config_passwd config_passwd

	log_info "$cloudinit_name $cloudinit_version finished"
}

main $@

#################################################################