Compare commits
No commits in common. "261d1ba557dc0299512c70513d3ffb435c103948" and "fe6b61ae17cc184b6097a8bf5429ea3839dcb170" have entirely different histories.
261d1ba557
...
fe6b61ae17
1
.gitignore
vendored
1
.gitignore
vendored
@ -1,3 +1,2 @@
|
|||||||
*.iso
|
*.iso
|
||||||
*.qcow2
|
*.qcow2
|
||||||
*.conf
|
|
||||||
|
61
README.md
61
README.md
@ -1,72 +1,17 @@
|
|||||||
# VMs
|
# VMs
|
||||||
|
|
||||||
## HOW-TO
|
## HOW-TO
|
||||||
|
To start (or create) a VM, go in the desired folder and run
|
||||||
To start (or create) a VM, go in the desired folder and run
|
|
||||||
```console
|
```console
|
||||||
$ ./run.sh [OPTS]
|
$ ./run.sh
|
||||||
```
|
```
|
||||||
|
|
||||||
You can pass `qemu` flags (see `QEMU(1)`) to `./run.sh` directly or you can
|
## USB passthrough
|
||||||
make theses flags permanent by editing `run.sh` (current VM only) or `lib.sh`
|
|
||||||
(all VMs).
|
|
||||||
|
|
||||||
### Headless
|
|
||||||
|
|
||||||
For a headless VM, just remove the `-vga` and `-audio` flags from `lib.sh`.<br>
|
|
||||||
To start the VM in the background: `./run.sh & disown`
|
|
||||||
|
|
||||||
### CPU/RAM limit
|
|
||||||
|
|
||||||
The CPU flag is not set by default, see `QEMU(1)` for default values.<br>
|
|
||||||
Default RAM flag: `-m "2G,maxmem=$((HOST_RAM - 2))G"`.
|
|
||||||
```
|
|
||||||
./run.sh -smp "${NB_CPUS},maxcpus=${MAX_CPUS}" \
|
|
||||||
-m "${RAM}G,maxmem=${MAX_RAM}G"
|
|
||||||
```
|
|
||||||
|
|
||||||
### Port forwarding
|
|
||||||
|
|
||||||
To forward host port 2222 to guest port 22:
|
|
||||||
```
|
|
||||||
./run.sh -nic user,hostfwd=tcp::2222-:22
|
|
||||||
```
|
|
||||||
|
|
||||||
### USB passthrough
|
|
||||||
|
|
||||||
If you need USB passthrough, uncomment and fill in the corresponding line in
|
If you need USB passthrough, uncomment and fill in the corresponding line in
|
||||||
`run.sh`.
|
`run.sh`.
|
||||||
[You may need root privileges](https://wiki.archlinux.org/title/QEMU#Pass-through_host_USB_device).
|
[You may need root privileges](https://wiki.archlinux.org/title/QEMU#Pass-through_host_USB_device).
|
||||||
|
|
||||||
## Windows installation
|
|
||||||
|
|
||||||
`Shift`+`F10` to open cmd.exe
|
|
||||||
```console
|
|
||||||
D:
|
|
||||||
pnputil /add-driver amd64\{version}\*.inf /install
|
|
||||||
|
|
||||||
diskpart
|
|
||||||
> list disk
|
|
||||||
> sel disk 0
|
|
||||||
> convert gpt
|
|
||||||
> create par efi size=100
|
|
||||||
> create par primary
|
|
||||||
> sel par 1
|
|
||||||
> format fs=fat32 quick
|
|
||||||
> assign letter=G:
|
|
||||||
> sel par 2
|
|
||||||
> format fs=ntfs quick
|
|
||||||
> assign letter=C:
|
|
||||||
> exit
|
|
||||||
|
|
||||||
E:
|
|
||||||
cd sources
|
|
||||||
dism /get-imageinfo /imagefile:install.wim
|
|
||||||
dism /apply-image /imagefile:install.wim /index:2 /applydir:C:
|
|
||||||
dism /image:C:\ /add-driver /driver:D:\amd64\{version}\viostor.inf
|
|
||||||
bcdboot C:\windows /s G: /f UEFI
|
|
||||||
```
|
|
||||||
|
|
||||||
## See also
|
## See also
|
||||||
|
|
||||||
<https://github.com/quickemu-project/quickemu>
|
<https://github.com/quickemu-project/quickemu>
|
||||||
|
15
android-x86/create.sh
Normal file
15
android-x86/create.sh
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
cd "$(dirname "$0")"
|
||||||
|
. ../lib.sh
|
||||||
|
|
||||||
|
if ! [ -f android.iso ]; then
|
||||||
|
ask_yn "android.iso not found, download?" \
|
||||||
|
&& bash ./download_isos.sh \
|
||||||
|
|| exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
qemu-img create -f qcow2 hda.qcow2 10G
|
||||||
|
|
||||||
|
qemu "$@" \
|
||||||
|
-drive file=android.iso,media=cdrom,readonly=on
|
||||||
|
#-device usb-host,vendorid=0xffff,productid=0xffff
|
5
android-x86/download_isos.sh
Executable file
5
android-x86/download_isos.sh
Executable file
@ -0,0 +1,5 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
|
||||||
|
android='https://sourceforge.net/projects/android-x86/files/latest/download'
|
||||||
|
|
||||||
|
curl -LC- -o android.iso "$android"
|
13
android-x86/run.sh
Executable file
13
android-x86/run.sh
Executable file
@ -0,0 +1,13 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
cd "$(dirname "$0")"
|
||||||
|
. ../lib.sh
|
||||||
|
|
||||||
|
if ! [ -f hda.qcow2 ]; then
|
||||||
|
ask_yn "hda.qcow2 not found, create?" \
|
||||||
|
&& bash ./create.sh \
|
||||||
|
|| exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
qemu "$@" \
|
||||||
|
-vga std \
|
||||||
|
#-device usb-host,vendorid=0xffff,productid=0xffff
|
@ -1,14 +1,16 @@
|
|||||||
#!/bin/bash -eu
|
#!/bin/bash -e
|
||||||
cd "$(dirname "$0")"
|
cd "$(dirname "$0")"
|
||||||
. ../lib.sh
|
. ../lib.sh
|
||||||
|
|
||||||
hda='https://geo.mirror.pkgbuild.com/images/latest/Arch-Linux-x86_64-basic.qcow2'
|
hda='https://geo.mirror.pkgbuild.com/images/latest/Arch-Linux-x86_64-basic.qcow2'
|
||||||
|
|
||||||
if ! [ -f hda.qcow2 ]; then
|
if ! [ -f hda.qcow2 ]; then
|
||||||
curl -Lo hda.qcow2 "$hda"
|
ask_yn "hda does not exist. Download?" \
|
||||||
|
&& curl -LC- -o hda.qcow2 "$hda" \
|
||||||
|
|| exit 1
|
||||||
fi
|
fi
|
||||||
|
|
||||||
echo "User: ${BOLD}${RED}arch:arch${NORMAL}"
|
echo -e 'User: \e[1m\e[31march:arch\e[0m'
|
||||||
read -rp 'Continue? '
|
read -rp 'Continue? '
|
||||||
|
|
||||||
qemu "$@" \
|
qemu "$@" \
|
||||||
|
@ -1,14 +1,16 @@
|
|||||||
#!/bin/bash -eu
|
#!/bin/bash -e
|
||||||
cd "$(dirname "$0")"
|
cd "$(dirname "$0")"
|
||||||
. ../lib.sh
|
. ../lib.sh
|
||||||
|
|
||||||
hda='https://cloud.debian.org/images/cloud/bookworm/latest/debian-12-nocloud-amd64.qcow2'
|
hda='https://cloud.debian.org/images/cloud/bookworm/latest/debian-12-nocloud-amd64.qcow2'
|
||||||
|
|
||||||
if ! [ -f hda.qcow2 ]; then
|
if ! [ -f hda.qcow2 ]; then
|
||||||
curl -Lo hda.qcow2 "$hda"
|
ask_yn "hda does not exist. Download?" \
|
||||||
|
&& curl -LC- -o hda.qcow2 "$hda" \
|
||||||
|
|| exit 1
|
||||||
fi
|
fi
|
||||||
|
|
||||||
echo "User: ${BOLD}${RED}root:${NORMAL}"
|
echo -e 'User: \e[1m\e[31mroot:\e[0m'
|
||||||
read -rp 'Continue? '
|
read -rp 'Continue? '
|
||||||
|
|
||||||
qemu "$@" \
|
qemu "$@" \
|
||||||
|
49
lib.sh
49
lib.sh
@ -1,34 +1,20 @@
|
|||||||
#!/bin/bash -eu
|
#!/bin/bash -e
|
||||||
DIR="$(dirname "${BASH_SOURCE[0]}")"
|
DIR="$(dirname "${BASH_SOURCE[0]}")"
|
||||||
|
|
||||||
BRIDGE=virbr0
|
BRIDGE=virbr0
|
||||||
|
|
||||||
NORMAL=$'\e[0m'
|
function ask_yn() {
|
||||||
BOLD=$'\e[1m'
|
local ans
|
||||||
RED=$'\e[31m'
|
|
||||||
|
|
||||||
ask_yn() {
|
printf '%s (Y/n) ' "$1" >&2
|
||||||
local a
|
read -r ans
|
||||||
|
case "${ans,,}" in
|
||||||
read -rp "$* (Y/n) " a
|
y*|'') return 0 ;;
|
||||||
[ -z "$a" ] || [[ "${a,,}" == y* ]]
|
*) return 1 ;;
|
||||||
|
esac
|
||||||
}
|
}
|
||||||
|
|
||||||
declare -A ISO
|
function _getmaxram() {
|
||||||
declare -a OPTS
|
|
||||||
download_isos() {
|
|
||||||
local curl file
|
|
||||||
|
|
||||||
curl=(curl -ZLC-)
|
|
||||||
for iso in "${!ISO[@]}"; do
|
|
||||||
file="$iso.iso"
|
|
||||||
curl+=(-o "$file" "${ISO[$iso]}")
|
|
||||||
OPTS+=(-drive "file=$file,media=cdrom,readonly=on")
|
|
||||||
done
|
|
||||||
"${curl[@]}"
|
|
||||||
}
|
|
||||||
|
|
||||||
_getmaxram() {
|
|
||||||
local ram; ram="$(free -g | awk '/^Mem:/{print $2 - 2}')"
|
local ram; ram="$(free -g | awk '/^Mem:/{print $2 - 2}')"
|
||||||
|
|
||||||
if [ "$ram" -le 2 ]; then ram=2
|
if [ "$ram" -le 2 ]; then ram=2
|
||||||
@ -36,7 +22,7 @@ _getmaxram() {
|
|||||||
echo "${ram}G"
|
echo "${ram}G"
|
||||||
}
|
}
|
||||||
|
|
||||||
_getnet() {
|
function _getnet() {
|
||||||
local net=user
|
local net=user
|
||||||
|
|
||||||
if ! ip link show "$BRIDGE" | grep -q UP; then
|
if ! ip link show "$BRIDGE" | grep -q UP; then
|
||||||
@ -48,26 +34,23 @@ _getnet() {
|
|||||||
echo "$net"
|
echo "$net"
|
||||||
}
|
}
|
||||||
|
|
||||||
qemu() {
|
function qemu() {
|
||||||
local ram=2G
|
|
||||||
local maxram; maxram="$(_getmaxram)"
|
local maxram; maxram="$(_getmaxram)"
|
||||||
local net; net="$(_getnet)"
|
local net; net="$(_getnet)"
|
||||||
|
|
||||||
(set -x
|
(set -x
|
||||||
qemu-system-x86_64 -accel kvm \
|
qemu-system-x86_64 -accel kvm \
|
||||||
-monitor stdio \
|
|
||||||
-M q35 \
|
-M q35 \
|
||||||
-bios /usr/share/edk2/x64/OVMF.4m.fd \
|
-bios /usr/share/ovmf/x64/OVMF.fd \
|
||||||
-cpu host \
|
-cpu host \
|
||||||
-m "$ram,maxmem=$maxram" \
|
-m "2G,maxmem=$maxram" \
|
||||||
-vga virtio \
|
-vga virtio \
|
||||||
-audio pipewire,model=hda \
|
|
||||||
-drive if=virtio,file=hda.qcow2 \
|
-drive if=virtio,file=hda.qcow2 \
|
||||||
|
-audio pipewire,model=hda \
|
||||||
-nic "model=virtio-net-pci,type=$net" \
|
-nic "model=virtio-net-pci,type=$net" \
|
||||||
-device qemu-xhci \
|
-device qemu-xhci \
|
||||||
-object "memory-backend-ram,id=mem,size=$ram,share=on" \
|
-object memory-backend-ram,id=mem,size=2G,share=on \
|
||||||
-numa node,memdev=mem \
|
-numa node,memdev=mem \
|
||||||
"${OPTS[@]}" \
|
|
||||||
"$@"
|
"$@"
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
76
startnat.sh
76
startnat.sh
@ -1,22 +1,22 @@
|
|||||||
#!/bin/bash -eu
|
#!/bin/bash -ex
|
||||||
DIR="$(dirname "${BASH_SOURCE[0]}")"
|
|
||||||
|
|
||||||
fix_nft_drops() {
|
function _iptables() {
|
||||||
local j h chain
|
local table="QEMU_$1"; shift
|
||||||
|
|
||||||
: > "$DIR/restore-nft.conf"
|
iptables -C "$table" "$@" 2> /dev/null || iptables -A "$table" "$@"
|
||||||
j="$(nft -j list chains | jq '.[][].chain | select(.policy == "drop")')"
|
|
||||||
while read -r h; do
|
|
||||||
mapfile -t chain < <(jq -r "select(.policy != \"accept\" and .hook == \"$h\") | .family,.table,.name,.policy" <<< "$j")
|
|
||||||
if [ -n "${chain[0]}" ]; then
|
|
||||||
nft add chain "${chain[0]}" "${chain[1]}" "${chain[2]}" '{ policy accept; }'
|
|
||||||
echo "add chain ${chain[0]} ${chain[1]} ${chain[2]} { policy ${chain[3]}; }" >> "$DIR/restore-nft.conf"
|
|
||||||
fi
|
|
||||||
done < <(nft -j list chains | jq -r '.[][].chain | select(.table == "qemu") | .hook')
|
|
||||||
}
|
}
|
||||||
|
|
||||||
command -V dnsmasq > /dev/null
|
function newtable() {
|
||||||
command -V nft > /dev/null
|
local table="$1"; shift
|
||||||
|
|
||||||
|
iptables -N "QEMU_$table" "$@" 2> /dev/null || true
|
||||||
|
iptables -A "$table" -j "QEMU_$table" "$@"
|
||||||
|
}
|
||||||
|
|
||||||
|
if ! command -v dnsmasq iptables-nft; then
|
||||||
|
echo 'missing 1+ dependencies: dnsmasq iptables-nft' >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
if [ "$EUID" != 0 ]; then
|
if [ "$EUID" != 0 ]; then
|
||||||
echo 'this script must be run as root' >&2
|
echo 'this script must be run as root' >&2
|
||||||
@ -24,41 +24,33 @@ if [ "$EUID" != 0 ]; then
|
|||||||
fi
|
fi
|
||||||
|
|
||||||
BRIDGE="${1-virbr0}"
|
BRIDGE="${1-virbr0}"
|
||||||
|
DEV="$(ip route | grep -Po '^default.*dev\s+\K\w+')"
|
||||||
|
|
||||||
modprobe nft_masq
|
|
||||||
sysctl net.ipv4.conf.all.forwarding=1
|
sysctl net.ipv4.conf.all.forwarding=1
|
||||||
|
|
||||||
if ! ip link show "$BRIDGE" 2> /dev/null; then
|
if ! ip link show "$BRIDGE" > /dev/null; then
|
||||||
ip link add "$BRIDGE" type bridge
|
ip link add "$BRIDGE" type bridge
|
||||||
fi
|
fi
|
||||||
|
|
||||||
ip link set dev "$BRIDGE" up
|
ip link set dev "$BRIDGE" up
|
||||||
|
|
||||||
ip address flush dev "$BRIDGE"
|
ip address flush dev "$BRIDGE"
|
||||||
ip address add 192.168.123.1/24 dev "$BRIDGE"
|
ip address add 192.168.122.1/24 dev "$BRIDGE"
|
||||||
|
|
||||||
nft -f- <<EOF
|
newtable INPUT
|
||||||
destroy table ip qemu;
|
newtable FORWARD
|
||||||
table ip qemu {
|
newtable OUTPUT
|
||||||
chain input {
|
newtable POSTROUTING -tnat
|
||||||
type filter hook input priority filter; policy accept;
|
|
||||||
iifname "$BRIDGE" counter
|
|
||||||
}
|
|
||||||
chain forward {
|
|
||||||
type filter hook forward priority filter; policy accept;
|
|
||||||
iifname "$BRIDGE" counter
|
|
||||||
}
|
|
||||||
chain postrouting {
|
|
||||||
type nat hook postrouting priority srcnat; policy accept;
|
|
||||||
masquerade
|
|
||||||
}
|
|
||||||
}
|
|
||||||
EOF
|
|
||||||
|
|
||||||
fix_nft_drops
|
_iptables INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
|
||||||
|
_iptables INPUT -i virbr0 -j ACCEPT
|
||||||
|
_iptables FORWARD -i "$BRIDGE" -o "$DEV" -j ACCEPT
|
||||||
|
_iptables FORWARD -i "$DEV" -o "$BRIDGE" -m state --state RELATED,ESTABLISHED -j ACCEPT
|
||||||
|
|
||||||
if ! pidof dnsmasq | grep -q "$(cat /var/run/dnsmasq-virbr0.pid)"; then
|
_iptables POSTROUTING -o "$DEV" -j MASQUERADE -tnat
|
||||||
dnsmasq -z \
|
|
||||||
|
pidof dnsmasq | grep -q "$(cat /var/run/dnsmasq-virbr0.pid)" \
|
||||||
|
|| dnsmasq --bind-dynamic \
|
||||||
-i "$BRIDGE" \
|
-i "$BRIDGE" \
|
||||||
-F 192.168.123.2,192.168.123.254,255.255.255.0 \
|
-F 192.168.122.2,192.168.122.254,255.255.255.0 \
|
||||||
-x /var/run/dnsmasq-virbr0.pid \
|
-x /var/run/dnsmasq-virbr0.pid
|
||||||
--server 1.1.1.1
|
|
||||||
fi
|
|
||||||
|
14
stopnat.sh
14
stopnat.sh
@ -1,4 +1,4 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash -x
|
||||||
|
|
||||||
if [ "$EUID" != 0 ]; then
|
if [ "$EUID" != 0 ]; then
|
||||||
echo "this script must be run as root" >&2
|
echo "this script must be run as root" >&2
|
||||||
@ -7,12 +7,14 @@ fi
|
|||||||
|
|
||||||
BRIDGE="${1-virbr0}"
|
BRIDGE="${1-virbr0}"
|
||||||
|
|
||||||
|
sysctl net.ipv4.conf.all.forwarding=0
|
||||||
|
|
||||||
ip link del dev "$BRIDGE"
|
ip link del dev "$BRIDGE"
|
||||||
|
|
||||||
nft destroy table qemu
|
iptables -S | sed -n '/QEMU/s/-A/iptables -D/p' | bash
|
||||||
if [ -f restore-nft.conf ]; then
|
iptables -S -tnat | sed -n '/QEMU/s/-A/iptables -tnat -D/p' | bash
|
||||||
nft -f ./restore-nft.conf
|
|
||||||
rm restore-nft.conf
|
iptables -S | sed -n '/QEMU/s/-N/iptables -X/p' | bash
|
||||||
fi
|
iptables -S -tnat | sed -n '/QEMU/s/-N/iptables -tnat -X/p' | bash
|
||||||
|
|
||||||
kill -TERM "$(cat /var/run/dnsmasq-virbr0.pid)"
|
kill -TERM "$(cat /var/run/dnsmasq-virbr0.pid)"
|
||||||
|
@ -1,17 +0,0 @@
|
|||||||
#!/bin/bash -eu
|
|
||||||
# vim: nowrap
|
|
||||||
cd "$(dirname "$0")"
|
|
||||||
. ../lib.sh
|
|
||||||
|
|
||||||
ISO=(
|
|
||||||
[win]='https://oemsoc.download.prss.microsoft.com/dbazure/X23-81951_26100.1742.240906-0331.ge_release_svc_refresh_CLIENT_ENTERPRISES_OEM_x64FRE_en-us.iso_640de540-87c4-427f-be87-e6d53a3a60b4?t=2c3b664b-b119-4088-9db1-ccff72c6d22e&P1=102816950270&P2=601&P3=2&P4=OC448onxqdmdUsBUApAiE8pj1FZ%2bEPTU3%2bC6Quq29MVwMyyDUtR%2fsbiy7RdVoZOHaZRndvzeOOnIwJZ2x3%2bmP6YK9cjJSP41Lvs0SulF4SVyL5C0DdDmiWqh2QW%2bcDPj2Xp%2bMrI9NOeElSBS5kkOWP8Eiyf2VkkQFM3g5vIk3HJVvu5sWo6pFKpFv4lML%2bHaIiTSuwbPMs5xwEQTfScuTKfigNlUZPdHRMp1B3uKLgIA3r0IbRpZgHYMXEwXQ%2fSLMdDNQthpqQvz1PThVkx7ObD55CXgt0GNSAWRfjdURWb8ywWk1gT7ozAgpP%2fKNm56U5nh33WZSuMZIuO1SBM2vw%3d%3d'
|
|
||||||
[virtio]='https://fedorapeople.org/groups/virt/virtio-win/direct-downloads/latest-virtio/virtio-win.iso'
|
|
||||||
)
|
|
||||||
|
|
||||||
if ! [ -f hda.qcow2 ]; then
|
|
||||||
qemu-img create -f qcow2 hda.qcow2 40G
|
|
||||||
download_isos
|
|
||||||
fi
|
|
||||||
|
|
||||||
qemu "$@" \
|
|
||||||
#-device usb-host,vendorid=0xffff,productid=0xffff
|
|
16
win2k22/create.sh
Normal file
16
win2k22/create.sh
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
cd "$(dirname "$0")"
|
||||||
|
. ../lib.sh
|
||||||
|
|
||||||
|
if ! [ -f win2k22.iso ] || ! [ -f virtio.iso ]; then
|
||||||
|
ask_yn "win2k22.iso and/or virtio.iso not found, download?" \
|
||||||
|
&& bash ./download_isos.sh \
|
||||||
|
|| exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
qemu-img create -f qcow2 hda.qcow2 40G
|
||||||
|
|
||||||
|
qemu "$@" \
|
||||||
|
-drive file=win2k22.iso,media=cdrom,readonly=on \
|
||||||
|
-drive file=virtio.iso,media=cdrom,readonly=on \
|
||||||
|
#-device usb-host,vendorid=0xffff,productid=0xffff
|
8
win2k22/download_isos.sh
Executable file
8
win2k22/download_isos.sh
Executable file
@ -0,0 +1,8 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
|
||||||
|
win2k22='https://go.microsoft.com/fwlink/p/?LinkID=2195280'
|
||||||
|
virtio='https://fedorapeople.org/groups/virt/virtio-win/direct-downloads/latest-virtio/virtio-win.iso'
|
||||||
|
|
||||||
|
curl -LC- \
|
||||||
|
-o win2k22.iso "$win2k22" \
|
||||||
|
-o virtio.iso "$virtio"
|
13
win2k22/run.sh
Executable file
13
win2k22/run.sh
Executable file
@ -0,0 +1,13 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
cd "$(dirname "$0")"
|
||||||
|
. ../lib.sh
|
||||||
|
|
||||||
|
if ! [ -f hda.qcow2 ]; then
|
||||||
|
ask_yn "hda.qcow2 not found, create?" \
|
||||||
|
&& bash ./create.sh \
|
||||||
|
|| exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
qemu "$@" \
|
||||||
|
-drive file=virtio.iso,media=cdrom,readonly=on \
|
||||||
|
#-device usb-host,vendorid=0xffff,productid=0xffff
|
Loading…
Reference in New Issue
Block a user