qemu-devel
[Top][All Lists]
Advanced

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

Re: [Qemu-devel] Fix writev syscall emulation


From: Kirill A. Shutemov
Subject: Re: [Qemu-devel] Fix writev syscall emulation
Date: Mon, 4 Feb 2008 22:36:46 +0200
User-agent: Mutt/1.5.17 (2007-11-01)

On [Mon, 04.02.2008 20:03], Richard Purdie wrote:
> Hi,
> 
> OpenEmbedded/Poky use qemu for locale generation when cross compiling.
> When we upgraded to qemu 0.9.1 it started giving locale generation
> errors on all 64 bit machines and some 32 bit ones.
> 
> I've traced it to the writev syscall failing. localedef passes several
> { NULL, 0 } iovec entries which trip up lock_iovec(). That function is
> returning an error for these but the return value isn't checked. The
> syscall is therefore always made but sometimes with a iovec that has
> only been half copied. If the total writes exceed size_t, EINVAL is
> returned by the kernel and glibc code emulates the call with a write
> which is most likely to happen on 32 bit so it sometimes works. size_t
> is unlikely to be exceeded on 64 bit so that returns an EFAULT and
> always corrupts/fails.
> 
> Anyhow, it seems 0 length iovec entries are allowed and we shouldn't
> care about the addresses in those cases. The patch below is one way to
> fix this. Ideally the return value of lock_iovec() needs be be checked
> too.
> 
> Regards,
> 
> Richard
> 
> ---
>  linux-user/syscall.c |    2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> Index: qemu-0.9.1/linux-user/syscall.c
> ===================================================================
> --- qemu-0.9.1.orig/linux-user/syscall.c      2008-02-03 00:00:00.000000000 
> +0000
> +++ qemu-0.9.1/linux-user/syscall.c   2008-02-03 00:00:38.000000000 +0000
> @@ -1048,7 +1048,7 @@ static abi_long lock_iovec(int type, str
>          base = tswapl(target_vec[i].iov_base);
>          vec[i].iov_len = tswapl(target_vec[i].iov_len);
>          vec[i].iov_base = lock_user(type, base, vec[i].iov_len, copy);
> -     if (!vec[i].iov_base) 
> +     if (!vec[i].iov_base && vec[i].iov_len) 
>              goto fail;
>      }
>      unlock_user (target_vec, target_addr, 0);

I have post similar patch some days ago.

-- 
Regards,  Kirill A. Shutemov
 + Belarus, Minsk
 + Velesys Ltd, http://www.velesys.com/
 + ALT Linux Team, http://www.altlinux.com/

Attachment: signature.asc
Description: Digital signature


reply via email to

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