]> git.proxmox.com Git - mirror_qemu.git/blame - scripts/qemu-binfmt-conf.sh
Merge remote-tracking branch 'remotes/armbru/tags/pull-misc-2018-07-16' into staging
[mirror_qemu.git] / scripts / qemu-binfmt-conf.sh
CommitLineData
08785f48 1#!/bin/sh
ecbed728 2# Enable automatic program execution by the kernel.
08785f48 3
bfe69cc8 4qemu_target_list="i386 i486 alpha arm armeb sparc32plus ppc ppc64 ppc64le m68k \
3bef0451 5mips mipsel mipsn32 mipsn32el mips64 mips64el \
ecbed728
RH
6sh4 sh4eb s390x aarch64 aarch64_be hppa riscv32 riscv64 xtensa xtensaeb \
7microblaze microblazeel or1k"
3bef0451
LV
8
9i386_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x03\x00'
daf238dc 10i386_mask='\xff\xff\xff\xff\xff\xfe\xfe\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
3bef0451
LV
11i386_family=i386
12
13i486_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x06\x00'
daf238dc 14i486_mask='\xff\xff\xff\xff\xff\xfe\xfe\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
3bef0451
LV
15i486_family=i386
16
17alpha_magic='\x7fELF\x02\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x26\x90'
daf238dc 18alpha_mask='\xff\xff\xff\xff\xff\xfe\xfe\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
3bef0451
LV
19alpha_family=alpha
20
21arm_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x28\x00'
22arm_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
23arm_family=arm
24
25armeb_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x28'
26armeb_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
2ced93ee 27armeb_family=armeb
3bef0451
LV
28
29sparc_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x02'
daf238dc 30sparc_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
3bef0451
LV
31sparc_family=sparc
32
33sparc32plus_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x12'
daf238dc 34sparc32plus_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
3bef0451
LV
35sparc32plus_family=sparc
36
37ppc_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x14'
38ppc_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
39ppc_family=ppc
40
41ppc64_magic='\x7fELF\x02\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x15'
42ppc64_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
43ppc64_family=ppc
44
45ppc64le_magic='\x7fELF\x02\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x15\x00'
46ppc64le_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\x00'
47ppc64le_family=ppcle
48
49m68k_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x04'
daf238dc 50m68k_mask='\xff\xff\xff\xff\xff\xff\xfe\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
3bef0451
LV
51m68k_family=m68k
52
53# FIXME: We could use the other endianness on a MIPS host.
54
55mips_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x08'
56mips_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
57mips_family=mips
58
59mipsel_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x08\x00'
60mipsel_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
61mipsel_family=mips
62
63mipsn32_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x08'
64mipsn32_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
65mipsn32_family=mips
66
67mipsn32el_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x08\x00'
68mipsn32el_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
69mipsn32el_family=mips
70
71mips64_magic='\x7fELF\x02\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x08'
72mips64_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
73mips64_family=mips
74
75mips64el_magic='\x7fELF\x02\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x08\x00'
76mips64el_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
77mips64el_family=mips
78
79sh4_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x2a\x00'
daf238dc 80sh4_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
3bef0451
LV
81sh4_family=sh4
82
83sh4eb_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x2a'
daf238dc 84sh4eb_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
3bef0451
LV
85sh4eb_family=sh4
86
87s390x_magic='\x7fELF\x02\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x16'
daf238dc 88s390x_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
3bef0451
LV
89s390x_family=s390x
90
91aarch64_magic='\x7fELF\x02\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\xb7\x00'
92aarch64_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
93aarch64_family=arm
94
f772f212
MW
95aarch64_be_magic='\x7fELF\x02\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\xb7'
96aarch64_be_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
2ced93ee 97aarch64_be_family=armeb
f772f212 98
e4d966cc
LV
99hppa_magic='\x7f\x45\x4c\x46\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x0f'
100hppa_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
101hppa_family=hppa
102
25fa194b
MC
103riscv32_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\xf3\x00'
104riscv32_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
105riscv32_family=riscv
106
107riscv64_magic='\x7fELF\x02\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\xf3\x00'
108riscv64_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
109riscv64_family=riscv
110
d4090306
MF
111xtensa_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x5e\x00'
112xtensa_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
113xtensa_family=xtensa
114
115xtensaeb_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x5e'
116xtensaeb_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
117xtensaeb_family=xtensaeb
118
947aeab3
LV
119microblaze_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\xba\xab'
120microblaze_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
121microblaze_family=microblaze
122
123microblazeel_magic='\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\xab\xba'
124microblazeel_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff'
125microblazeel_family=microblazeel
126
ecbed728
RH
127or1k_magic='\x7fELF\x01\x02\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x5c'
128or1k_mask='\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff'
129or1k_family=or1k
130
3bef0451
LV
131qemu_get_family() {
132 cpu=${HOST_ARCH:-$(uname -m)}
133 case "$cpu" in
134 amd64|i386|i486|i586|i686|i86pc|BePC|x86_64)
135 echo "i386"
136 ;;
137 mips*)
138 echo "mips"
139 ;;
140 "Power Macintosh"|ppc64|powerpc|ppc)
141 echo "ppc"
142 ;;
143 ppc64el|ppc64le)
144 echo "ppcle"
145 ;;
2ced93ee 146 arm|armel|armhf|arm64|armv[4-9]*l|aarch64)
3bef0451
LV
147 echo "arm"
148 ;;
2ced93ee
MW
149 armeb|armv[4-9]*b|aarch64_be)
150 echo "armeb"
151 ;;
3bef0451
LV
152 sparc*)
153 echo "sparc"
154 ;;
25fa194b
MC
155 riscv*)
156 echo "riscv"
157 ;;
3bef0451
LV
158 *)
159 echo "$cpu"
160 ;;
161 esac
162}
163
164usage() {
165 cat <<EOF
166Usage: qemu-binfmt-conf.sh [--qemu-path PATH][--debian][--systemd CPU]
167 [--help][--credential yes|no][--exportdir PATH]
7155be7c 168 [--persistent yes|no][--qemu-suffix SUFFIX]
3bef0451
LV
169
170 Configure binfmt_misc to use qemu interpreter
171
7155be7c
LV
172 --help: display this usage
173 --qemu-path: set path to qemu interpreter ($QEMU_PATH)
174 --qemu-suffix: add a suffix to the default interpreter name
175 --debian: don't write into /proc,
176 instead generate update-binfmts templates
177 --systemd: don't write into /proc,
178 instead generate file for systemd-binfmt.service
179 for the given CPU. If CPU is "ALL", generate a
180 file for all known cpus
181 --exportdir: define where to write configuration files
182 (default: $SYSTEMDDIR or $DEBIANDIR)
183 --credential: if yes, credential and security tokens are
184 calculated according to the binary to interpret
185 --persistent: if yes, the interpreter is loaded when binfmt is
186 configured and remains in memory. All future uses
187 are cloned from the open file.
3bef0451
LV
188
189 To import templates with update-binfmts, use :
190
191 sudo update-binfmts --importdir ${EXPORTDIR:-$DEBIANDIR} --import qemu-CPU
192
193 To remove interpreter, use :
194
195 sudo update-binfmts --package qemu-CPU --remove qemu-CPU $QEMU_PATH
196
197 With systemd, binfmt files are loaded by systemd-binfmt.service
198
199 The environment variable HOST_ARCH allows to override 'uname' to generate
200 configuration files for a different architecture than the current one.
201
202 where CPU is one of:
203
204 $qemu_target_list
205
206EOF
207}
208
209qemu_check_access() {
210 if [ ! -w "$1" ] ; then
211 echo "ERROR: cannot write to $1" 1>&2
212 exit 1
213 fi
214}
215
216qemu_check_bintfmt_misc() {
217 # load the binfmt_misc module
218 if [ ! -d /proc/sys/fs/binfmt_misc ]; then
219 if ! /sbin/modprobe binfmt_misc ; then
220 exit 1
221 fi
222 fi
223 if [ ! -f /proc/sys/fs/binfmt_misc/register ]; then
224 if ! mount binfmt_misc -t binfmt_misc /proc/sys/fs/binfmt_misc ; then
225 exit 1
226 fi
227 fi
228
229 qemu_check_access /proc/sys/fs/binfmt_misc/register
230}
231
232installed_dpkg() {
233 dpkg --status "$1" > /dev/null 2>&1
234}
235
236qemu_check_debian() {
237 if [ ! -e /etc/debian_version ] ; then
238 echo "WARNING: your system is not a Debian based distro" 1>&2
239 elif ! installed_dpkg binfmt-support ; then
240 echo "WARNING: package binfmt-support is needed" 1>&2
241 fi
242 qemu_check_access "$EXPORTDIR"
243}
244
245qemu_check_systemd() {
246 if ! systemctl -q is-enabled systemd-binfmt.service ; then
247 echo "WARNING: systemd-binfmt.service is missing or disabled" 1>&2
248 fi
249 qemu_check_access "$EXPORTDIR"
250}
251
252qemu_generate_register() {
70a77984
LV
253 flags=""
254 if [ "$CREDENTIAL" = "yes" ] ; then
255 flags="OC"
256 fi
01ecd22a
LV
257 if [ "$PERSISTENT" = "yes" ] ; then
258 flags="${flags}F"
259 fi
70a77984
LV
260
261 echo ":qemu-$cpu:M::$magic:$mask:$qemu:$flags"
3bef0451
LV
262}
263
264qemu_register_interpreter() {
265 echo "Setting $qemu as binfmt interpreter for $cpu"
266 qemu_generate_register > /proc/sys/fs/binfmt_misc/register
267}
268
269qemu_generate_systemd() {
270 echo "Setting $qemu as binfmt interpreter for $cpu for systemd-binfmt.service"
271 qemu_generate_register > "$EXPORTDIR/qemu-$cpu.conf"
272}
273
274qemu_generate_debian() {
275 cat > "$EXPORTDIR/qemu-$cpu" <<EOF
276package qemu-$cpu
277interpreter $qemu
278magic $magic
279mask $mask
70a77984 280credential $CREDENTIAL
3bef0451 281EOF
3bef0451
LV
282}
283
284qemu_set_binfmts() {
285 # probe cpu type
286 host_family=$(qemu_get_family)
287
288 # register the interpreter for each cpu except for the native one
289
290 for cpu in ${qemu_target_list} ; do
291 magic=$(eval echo \$${cpu}_magic)
292 mask=$(eval echo \$${cpu}_mask)
293 family=$(eval echo \$${cpu}_family)
294
295 if [ "$magic" = "" ] || [ "$mask" = "" ] || [ "$family" = "" ] ; then
296 echo "INTERNAL ERROR: unknown cpu $cpu" 1>&2
297 continue
298 fi
299
300 qemu="$QEMU_PATH/qemu-$cpu"
301 if [ "$cpu" = "i486" ] ; then
302 qemu="$QEMU_PATH/qemu-i386"
303 fi
304
7155be7c 305 qemu="$qemu$QEMU_SUFFIX"
3bef0451
LV
306 if [ "$host_family" != "$family" ] ; then
307 $BINFMT_SET
308 fi
309 done
310}
311
312CHECK=qemu_check_bintfmt_misc
313BINFMT_SET=qemu_register_interpreter
314
315SYSTEMDDIR="/etc/binfmt.d"
316DEBIANDIR="/usr/share/binfmts"
317
318QEMU_PATH=/usr/local/bin
70a77984 319CREDENTIAL=no
01ecd22a 320PERSISTENT=no
7155be7c 321QEMU_SUFFIX=""
3bef0451 322
7155be7c 323options=$(getopt -o ds:Q:S:e:hc:p: -l debian,systemd:,qemu-path:,qemu-suffix:,exportdir:,help,credential:,persistent: -- "$@")
3bef0451
LV
324eval set -- "$options"
325
326while true ; do
327 case "$1" in
328 -d|--debian)
329 CHECK=qemu_check_debian
330 BINFMT_SET=qemu_generate_debian
331 EXPORTDIR=${EXPORTDIR:-$DEBIANDIR}
332 ;;
333 -s|--systemd)
334 CHECK=qemu_check_systemd
335 BINFMT_SET=qemu_generate_systemd
336 EXPORTDIR=${EXPORTDIR:-$SYSTEMDDIR}
337 shift
338 # check given cpu is in the supported CPU list
3ff48453
LV
339 if [ "$1" != "ALL" ] ; then
340 for cpu in ${qemu_target_list} ; do
341 if [ "$cpu" = "$1" ] ; then
342 break
343 fi
344 done
345
6f75023a 346 if [ "$cpu" = "$1" ] ; then
3ff48453
LV
347 qemu_target_list="$1"
348 else
349 echo "ERROR: unknown CPU \"$1\"" 1>&2
350 usage
351 exit 1
3bef0451 352 fi
3bef0451
LV
353 fi
354 ;;
355 -Q|--qemu-path)
356 shift
357 QEMU_PATH="$1"
358 ;;
7155be7c
LV
359 -F|--qemu-suffix)
360 shift
361 QEMU_SUFFIX="$1"
362 ;;
3bef0451
LV
363 -e|--exportdir)
364 shift
365 EXPORTDIR="$1"
366 ;;
367 -h|--help)
368 usage
369 exit 1
370 ;;
371 -c|--credential)
372 shift
70a77984 373 CREDENTIAL="$1"
3bef0451 374 ;;
01ecd22a
LV
375 -p|--persistent)
376 shift
377 PERSISTENT="$1"
3bef0451
LV
378 ;;
379 *)
380 break
381 ;;
382 esac
383 shift
384done
385
386$CHECK
387qemu_set_binfmts