summaryrefslogtreecommitdiff
path: root/tools/uncloud-init
blob: 2574d48213285e86064827077591744f4ecfe48c (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
#!/bin/sh
# vi: ts=4 noexpandtab

# This script is meant to "kvmify" an image.  Its not meant to be
# terribly robust, or a good idea to ever run in a "real image".
# its' only intended method of invocation is from the kernel as 'init'
# in which case it will then invoke /sbin/init after it is done
#  init=/path/to/kvmify-init

KEY="xupdate"
UMOUNT=""
RMDIR=""
MARK=/var/lib/cloud/sem/uncloud-init.once
ROOT_RW=""

doexec() {
	if [ -n "$ROOT_RW" ]; then
		mkdir -p "${MARK%/*}";
		date > "${MARK}";
	fi
	cleanup;
	log "invoking /sbin/init $*"
	exec /sbin/init "$@";
}
log() { echo "::${0##*/}:" "$@"; }
cleanup() {
	[ -z "${UMOUNT}" ] || { umount "${UMOUNT}" && unset UMOUNT; }
	[ -z "${RMDIR}" ] || { rm -Rf "${RMDIR}" && unset RMDIR; }
	[ -z "${ROOT_RW}" ] || { mount -o remount,ro / ; unset ROOT_RW; }
}

updateFrom() {
	local dev=$1 fmt=$2
	local mp="";

	[ "${fmt}" = "tar" -o "${fmt}" = "mnt" ] ||
		{ log FAIL "unknown format ${fmt}"; return 1; }

	log INFO "updating from ${dev} format ${fmt}"
		[ ! -e "${dev}" -a -e "/dev/${dev}" ] && dev="/dev/${dev}"
	[ -e "${dev}" ] || { echo "no file $dev"; return 2; }

	mp=$(mktemp -d "${TEMPDIR:-/tmp}/update.XXXXXX") && 
		RMDIR="${mp}" ||
		{ log FAIL "failed to mktemp"; return 1; }

	if [ "$fmt" = "tar" ]; then
		dd "if=${dev}" | ( tar -C "${mp}" -xf - ) ||
			{ log FAIL "failed to extract ${dev}"; return 1; }
	elif [ "$fmt" = "mnt" ]; then
		mount -o ro "${dev}" "${mp}" && UMOUNT=${mp} ||
			{ log FAIL "failed mount ${mp}"; return 1; }
	else
		log FAIL "unknown format ${fmt}"; return 1;
	fi

	if [ -d "${mp}/updates" ]; then
		rsync -av "${mp}/updates/" "/" ||
			{ log FAIL "failed rsync updates/ /"; return 1; }
	fi
	if [ -f "${mp}/updates.tar" ]; then
		tar -C / -xvf "${mp}/updates.tar" ||
			{ log FAIL "failed tar -C / -xvf ${mp}/updates.tar"; return 1; }
	fi
	script="${mp}/updates.script"
	if [ -f "${script}" -a -x "${script}" ]; then
		MP_DIR=${mp} "${mp}/updates.script" ||
			{ log FAIL "failed to run updates.script"; return 1; }
	fi
}

fail() { { [ $# -eq 0 ] && log "FAILING" ; } || log "$@"; exit 1; }

[ -s "$MARK" ] && { log "already updated" ; doexec "$@"; }

mount -o remount,rw / || fail "failed to mount rw"
ROOT_RW=1

if [ ! -e /proc/cmdline ]; then
	mount -t proc /proc /proc
	read cmdline < /proc/cmdline
	umount /proc
else
	read cmdline < /proc/cmdline
fi

ubuntu_pass=""

for x in ${cmdline}; do
	case "$x" in
		${KEY}=*)
			val=${x#${KEY}=}
			dev=${val%:*}
			[ "${dev}" = "${val}" ] && fmt="" || fmt=${val#${dev}:}
			log "update from ${dev},${fmt}"
			updateFrom "${dev}" "${fmt}" || fail "update failed"
			log "end update  ${dev},${fmt}"
			;;
		ubuntu-pass=*|ubuntu_pass=*) ubuntu_pass=${x#*=};;
		helpmount) helpmount=1;;
		root=*) rootspec=${x#root=};;
	esac
done

if [ "${ubuntu_pass}" = "R" -o "${ubuntu_pass}" = "random" ]; then
	ubuntu_pass=$(python -c 'import string, random;
random.seed(); print "".join(random.sample(string.letters+string.digits, 8))')
	log "settting ubuntu pass = ${ubuntu_pass}" 
	printf "\n===\nubuntu_pass = %s\n===\n" "${ubuntu_pass}" >/dev/ttyS0
fi

[ -z "${ubuntu_pass}" ] ||
	printf "ubuntu:%s\n" "${ubuntu_pass}" > /root/ubuntu-user-pass

if [ -e /root/ubuntu-user-pass ]; then
	log "changing ubuntu user's password!"
	chpasswd < /root/ubuntu-user-pass ||
	log "FAIL: failed changing pass"
fi

cp /etc/init/tty2.conf /etc/init/ttyS0.conf &&
	sed -i s,tty2,ttyS0,g /etc/init/ttyS0.conf 2>/dev/null &&
	log "enabled console on ttyS0"

pa=PasswordAuthentication
sed -i "s,${pa} no,${pa} yes," /etc/ssh/sshd_config 2>/dev/null &&
	log "enabled passwd auth in ssh" ||
	log "failed to enable passwd ssh"

grep -q vga16fb /etc/modprobe.d/blacklist.conf || {
	echo "blacklist vga16fb" >> /etc/modprobe.d/blacklist.conf &&
	log "blacklisted vga16fb"
}

#lstr="${rootspec}"
#if ! grep -q "^${lstr}[[:space:]]" /etc/fstab; then
#	log "changing / in /etc/ftab to agree with cmdline (${lstr}) (bug 509841)"
#	sed -i "s,^\([^[[:space:]#]\+\)\([[:space:]]\+\)/\([[:space:]]\+\),${lstr}\2/\3," /etc/fstab
#fi

doexec "$@"