mbox series

[00/12] Introduce new vmapple machine type

Message ID 20230614224038.86148-1-graf@amazon.com (mailing list archive)
Headers show
Series Introduce new vmapple machine type | expand

Message

Alexander Graf June 14, 2023, 10:40 p.m. UTC
This patch set introduces a new ARM and HVF specific machine type
called "vmapple". It mimicks the device model that Apple's proprietary
Virtualization.Framework exposes, but implements it in QEMU.

With this new machine type, you can run macOS guests on Apple Silicon
systems via HVF. To do so, you need to first install macOS using
Virtualization.Framework onto a virtual disk image using a tool like
macosvm (https://github.com/s-u/macosvm)

  $ macosvm --disk disk.img,size=32g --aux aux.img \
            --restore UniversalMac_12.0.1_21A559_Restore.ipsw vm.json

Then, extract the ECID from the installed VM:

  $ cat "$DIR/macosvm.json" | python3 -c                                 \
  'import json,sys;obj=json.load(sys.stdin);print(obj["machineId"]) |    \
  base64 -d | plutil -extract ECID raw -

In addition, cut off the first 16kb of the aux.img:

  $ dd if=aux.img of=aux.img.trimmed bs=$(( 0x4000 )) skip=1

Now, you can just launch QEMU with the bits generated above:

  $ qemu-system-aarch64 -serial mon:stdio                                \
  -m 4G                                                                  \
  -M vmapple,uuid=6240349656165161789                                    \
  -bios /Sys*/Lib*/Fra*/Virtualization.f*/R*/AVPBooter.vmapple2.bin      \
  -pflash aux.img.trimmed                                                \
  -pflash disk.img                                                       \
  -drive file=disk.img,if=none,id=root                                   \
  -device virtio-blk-pci,drive=root,x-apple-type=1                       \
  -drive file=aux.img.trimmed,if=none,id=aux                             \
  -device virtio-blk-pci,drive=aux,x-apple-type=2                        \
  -accel hvf -no-reboot

There are a few limitations with this implementation:

  - Only runs on macOS because it relies on
    ParavirtualizesGraphics.Framework
  - Something is not fully correct on interrupt delivery or
    similar - the keyboard does not work
  - No Rosetta in the guest because we lack the private
    entitlement to enable TSO

Over time, I hope that some of the limitations above could cease to exist.
This device model would enable very nice use cases with KVM on an Asahi
Linux device.


Alexander Graf (12):
  build: Only define OS_OBJECT_USE_OBJC with gcc
  hw/misc/pvpanic: Add MMIO interface
  hvf: Increase number of possible memory slots
  hvf: arm: Ignore writes to CNTP_CTL_EL0
  hw/virtio: Add support for apple virtio-blk
  hw: Add vmapple subdir
  gpex: Allow more than 4 legacy IRQs
  hw/vmapple/aes: Introduce aes engine
  hw/vmapple/bdif: Introduce vmapple backdoor interface
  hw/vmapple/cfg: Introduce vmapple cfg region
  hw/vmapple/apple-gfx: Introduce ParavirtualizedGraphics.Framework
    support
  hw/vmapple/vmapple: Add vmapple machine type

 MAINTAINERS                                 |   6 +
 accel/hvf/hvf-accel-ops.c                   |   2 +-
 hw/Kconfig                                  |   1 +
 hw/arm/sbsa-ref.c                           |   2 +-
 hw/arm/virt.c                               |   2 +-
 hw/block/virtio-blk.c                       |  23 +
 hw/i386/microvm.c                           |   2 +-
 hw/loongarch/virt.c                         |   2 +-
 hw/meson.build                              |   1 +
 hw/mips/loongson3_virt.c                    |   2 +-
 hw/misc/Kconfig                             |   4 +
 hw/misc/meson.build                         |   1 +
 hw/misc/pvpanic-mmio.c                      |  66 ++
 hw/openrisc/virt.c                          |  12 +-
 hw/pci-host/gpex.c                          |  36 +-
 hw/riscv/virt.c                             |  12 +-
 hw/virtio/virtio-blk-pci.c                  |   7 +
 hw/vmapple/Kconfig                          |  30 +
 hw/vmapple/aes.c                            | 583 +++++++++++++++++
 hw/vmapple/apple-gfx.m                      | 578 +++++++++++++++++
 hw/vmapple/bdif.c                           | 245 ++++++++
 hw/vmapple/cfg.c                            | 105 ++++
 hw/vmapple/meson.build                      |   5 +
 hw/vmapple/trace-events                     |  47 ++
 hw/vmapple/trace.h                          |   1 +
 hw/vmapple/vmapple.c                        | 661 ++++++++++++++++++++
 hw/xtensa/virt.c                            |   2 +-
 include/hw/misc/pvpanic.h                   |   1 +
 include/hw/pci-host/gpex.h                  |   7 +-
 include/hw/pci/pci_ids.h                    |   1 +
 include/hw/virtio/virtio-blk.h              |   1 +
 include/hw/vmapple/bdif.h                   |  31 +
 include/hw/vmapple/cfg.h                    |  68 ++
 include/standard-headers/linux/virtio_blk.h |   3 +
 include/sysemu/hvf_int.h                    |   2 +-
 meson.build                                 |   9 +-
 target/arm/hvf/hvf.c                        |   7 +
 37 files changed, 2538 insertions(+), 30 deletions(-)
 create mode 100644 hw/misc/pvpanic-mmio.c
 create mode 100644 hw/vmapple/Kconfig
 create mode 100644 hw/vmapple/aes.c
 create mode 100644 hw/vmapple/apple-gfx.m
 create mode 100644 hw/vmapple/bdif.c
 create mode 100644 hw/vmapple/cfg.c
 create mode 100644 hw/vmapple/meson.build
 create mode 100644 hw/vmapple/trace-events
 create mode 100644 hw/vmapple/trace.h
 create mode 100644 hw/vmapple/vmapple.c
 create mode 100644 include/hw/vmapple/bdif.h
 create mode 100644 include/hw/vmapple/cfg.h

Comments

Mads Ynddal June 20, 2023, 11:17 a.m. UTC | #1
> On 15 Jun 2023, at 00.40, Alexander Graf <graf@amazon.com> wrote:
> 
> This patch set introduces a new ARM and HVF specific machine type
> called "vmapple". It mimicks the device model that Apple's proprietary
> Virtualization.Framework exposes, but implements it in QEMU.
> 
> With this new machine type, you can run macOS guests on Apple Silicon
> systems via HVF. To do so, you need to first install macOS using
> Virtualization.Framework onto a virtual disk image using a tool like
> macosvm (https://github.com/s-u/macosvm)
> 
>  $ macosvm --disk disk.img,size=32g --aux aux.img \
>            --restore UniversalMac_12.0.1_21A559_Restore.ipsw vm.json
> 
> Then, extract the ECID from the installed VM:
> 
>  $ cat "$DIR/macosvm.json" | python3 -c                                 \
>  'import json,sys;obj=json.load(sys.stdin);print(obj["machineId"]) |    \
>  base64 -d | plutil -extract ECID raw -

Beware, that the file will be called 'vm.json' and DIR is undefined following
the previous line. Also, it's missing a single-quote at the end of
`["machineId"])`.

> In addition, cut off the first 16kb of the aux.img:
> 
>  $ dd if=aux.img of=aux.img.trimmed bs=$(( 0x4000 )) skip=1
> 
> Now, you can just launch QEMU with the bits generated above:
> 
>  $ qemu-system-aarch64 -serial mon:stdio                                \
>  -m 4G                                                                  \
>  -M vmapple,uuid=6240349656165161789                                    \
>  -bios /Sys*/Lib*/Fra*/Virtualization.f*/R*/AVPBooter.vmapple2.bin      \
>  -pflash aux.img.trimmed                                                \
>  -pflash disk.img                                                       \
>  -drive file=disk.img,if=none,id=root                                   \
>  -device virtio-blk-pci,drive=root,x-apple-type=1                       \
>  -drive file=aux.img.trimmed,if=none,id=aux                             \
>  -device virtio-blk-pci,drive=aux,x-apple-type=2                        \
>  -accel hvf -no-reboot

Just for clarity, I'd add that the 'vmapple,uuid=...' has to be set to the
ECID the previous step.

You haven't defined a display, but I'm not sure if that is on purpose to
show a minimal setup. I had to add '-display sdl' for it to fully work.

> There are a few limitations with this implementation:
> 
>  - Only runs on macOS because it relies on
>    ParavirtualizesGraphics.Framework
>  - Something is not fully correct on interrupt delivery or
>    similar - the keyboard does not work
>  - No Rosetta in the guest because we lack the private
>    entitlement to enable TSO

Would it be possible to mitigate the keyboard issue using an emulated USB
keyboard? I tried poking around with it, but with no success.

> Over time, I hope that some of the limitations above could cease to exist.
> This device model would enable very nice use cases with KVM on an Asahi
> Linux device.
Alexander Graf June 21, 2023, 1:23 p.m. UTC | #2
Hi Mads,


On 20.06.23 13:17, Mads Ynddal wrote:

>
>> On 15 Jun 2023, at 00.40, Alexander Graf <graf@amazon.com> wrote:
>>
>> This patch set introduces a new ARM and HVF specific machine type
>> called "vmapple". It mimicks the device model that Apple's proprietary
>> Virtualization.Framework exposes, but implements it in QEMU.
>>
>> With this new machine type, you can run macOS guests on Apple Silicon
>> systems via HVF. To do so, you need to first install macOS using
>> Virtualization.Framework onto a virtual disk image using a tool like
>> macosvm (https://github.com/s-u/macosvm)
>>
>>   $ macosvm --disk disk.img,size=32g --aux aux.img \
>>             --restore UniversalMac_12.0.1_21A559_Restore.ipsw vm.json
>>
>> Then, extract the ECID from the installed VM:
>>
>>   $ cat "$DIR/macosvm.json" | python3 -c                                 \
>>   'import json,sys;obj=json.load(sys.stdin);print(obj["machineId"]) |    \
>>   base64 -d | plutil -extract ECID raw -
> Beware, that the file will be called 'vm.json' and DIR is undefined following
> the previous line. Also, it's missing a single-quote at the end of
> `["machineId"])`.


Thanks :)


>
>> In addition, cut off the first 16kb of the aux.img:
>>
>>   $ dd if=aux.img of=aux.img.trimmed bs=$(( 0x4000 )) skip=1
>>
>> Now, you can just launch QEMU with the bits generated above:
>>
>>   $ qemu-system-aarch64 -serial mon:stdio                                \
>>   -m 4G                                                                  \
>>   -M vmapple,uuid=6240349656165161789                                    \
>>   -bios /Sys*/Lib*/Fra*/Virtualization.f*/R*/AVPBooter.vmapple2.bin      \
>>   -pflash aux.img.trimmed                                                \
>>   -pflash disk.img                                                       \
>>   -drive file=disk.img,if=none,id=root                                   \
>>   -device virtio-blk-pci,drive=root,x-apple-type=1                       \
>>   -drive file=aux.img.trimmed,if=none,id=aux                             \
>>   -device virtio-blk-pci,drive=aux,x-apple-type=2                        \
>>   -accel hvf -no-reboot
> Just for clarity, I'd add that the 'vmapple,uuid=...' has to be set to the
> ECID the previous step.
>
> You haven't defined a display, but I'm not sure if that is on purpose to
> show a minimal setup. I had to add '-display sdl' for it to fully work.


Weird, I do get a normal cocoa output screen by default.


>
>> There are a few limitations with this implementation:
>>
>>   - Only runs on macOS because it relies on
>>     ParavirtualizesGraphics.Framework
>>   - Something is not fully correct on interrupt delivery or
>>     similar - the keyboard does not work
>>   - No Rosetta in the guest because we lack the private
>>     entitlement to enable TSO
> Would it be possible to mitigate the keyboard issue using an emulated USB
> keyboard? I tried poking around with it, but with no success.


Unfortunately I was not able to get USB stable inside the guest. This 
may be an issue with interrupt propagation: With usb-kbd I see macOS not 
pick up key up or down events in time.


Alex





Amazon Development Center Germany GmbH
Krausenstr. 38
10117 Berlin
Geschaeftsfuehrung: Christian Schlaeger, Jonathan Weiss
Eingetragen am Amtsgericht Charlottenburg unter HRB 149173 B
Sitz: Berlin
Ust-ID: DE 289 237 879