qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Qemu-devel] [PATCH 14/17] PPC: dbdma: Support unaligned DMA access


From: Kevin Wolf
Subject: Re: [Qemu-devel] [PATCH 14/17] PPC: dbdma: Support unaligned DMA access
Date: Wed, 17 Jul 2013 11:09:30 +0200
User-agent: Mutt/1.5.21 (2010-09-15)

Am 01.07.2013 um 02:13 hat Alexander Graf geschrieben:
> The DBDMA engine really just reads bytes from a producing device (IDE
> in our case) and shoves these bytes into memory. It doesn't care whether
> any alignment takes place or not.
> 
> Our code today however assumes that block accesses always happen on
> sector (512 byte) boundaries. This is a fair assumption for most cases.
> 
> However, Mac OS X really likes to do unaligned, incomplete accesses
> that it finishes with the next DMA request.
> 
> So we need to read / write the unaligned bits independent of the actual
> asynchronous request, because that one can only handle 512-byte-aligned
> data. We also need to cache these unaligned sectors until the next DMA
> request, at which point the data might be successfully flushed from the
> pipe.
> 
> Signed-off-by: Alexander Graf <address@hidden>

> @@ -98,14 +122,40 @@ static void pmac_ide_atapi_transfer_cb(void *opaque, int 
> ret)
>  
>      /* launch next transfer */
>  
> -    MACIO_DPRINTF("io->len = %#x\n", io->len);
> +    /* handle unaligned accesses first, get them over with and only do the
> +       remaining bulk transfer using our async DMA helpers */
> +    unaligned = io->len & 0x1ff;
> +    if (unaligned) {
> +        int sector_num = (s->lba << 2) + (s->io_buffer_index >> 9);
> +        int nsector = io->len >> 9;
>  
> -    s->io_buffer_size = io->len;
> +        MACIO_DPRINTF("precopying unaligned %d bytes to %#lx\n",
> +                      unaligned, io->addr + io->len - unaligned);
> +
> +        bdrv_read(s->bs, sector_num + nsector, io->remainder, 1);

I haven't really reviewed the general logic, but not using the return
value of bdrv_read() and bdrv_write() is most definitely wrong, I/O can
fail. More instances of the same bug follow.

Kevin



reply via email to

[Prev in Thread] Current Thread [Next in Thread]