Re: [PATCH 0/3] virtio-mmio: handle BE guests on LE hosts

Marc Zyngier
2013-10-15T09:20:04Z

On 15/10/13 07:38, Michael S. Tsirkin wrote:
> On Tue, Oct 15, 2013 at 09:53:17AM +1030, Rusty Russell wrote:
>> "Michael S. Tsirkin" <mst@redhat.com> writes:
>>> On Mon, Oct 14, 2013 at 06:50:48PM +0200, Paolo Bonzini wrote:
>>>> Il 14/10/2013 17:36, Marc Zyngier ha scritto:
>>>>>>>
>>>>>>> Devices are fine in QEMU, it's only the "generic" parts (rings) that are
>>>>>>> missing AFAICT.
>>>>> So if I understand correctly how it works, target endianness is set at
>>>>> compile time, and you have a BE specific QEMU?
>>>>
>>>> Yes. Though as Alex said, this will have to change for PPC
>>>> little-endian support.
>>>>
>>>> Paolo
>>>
>>> Or we'll just say that this platform requires virtio 1.0.
>>
>> To come full circle, I have implemented virtio support for BE PPC in
>> qemu :) And we'll be supporting pre-1.0 for the moment. I'm awaiting
>> some ppc-specific hooks, but it could be merged without them.
>>
>> It's icky: we don't really want to use the current endianness of the
>> CPU, since in theory a BE kernel could be running an LE process. So at
>> the time of virtio device reset (the first thing the Linux drivers do)
>> we read the endianness of the interrupt entry point, which is presumably
>> the OS endianness.
>
> Indeed, ick.
> The next thing after reset is status write:
>
> /* We always start by resetting the device, in case a previous
> * driver messed it up. This also tests that code path a
> * little. */
> dev->config->reset(dev);
>
> /* Acknowledge that we've seen the device. */
> add_status(dev, VIRTIO_CONFIG_S_ACKNOWLEDGE);
>
> and mmio happens to use a 32 bit register for this:
>
> static void vm_set_status(struct virtio_device *vdev, u8 status)
> {
> struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);
>
> /* We should never be setting status to 0. */
> BUG_ON(status == 0);
>
> writel(status, vm_dev->base + VIRTIO_MMIO_STATUS);
> }
>
> so if we only care about mmio, we can use the status write
> to detect endian-ness: low byte set means LE, high byte set
> means BE, which seems cleaner.
>
> Hmm?

Don't think it works. MMIO is LE only, so the interesting byte will
always be at the same location (writel will do the swap).

M.
--
Jazz is not dead. It just smells funny...