LockDIBSection problem
Rein Klazes
wijn at wanadoo.nl
Sun May 8 14:43:22 CDT 2005
On 06 May 2005 16:01:06 +0200, you wrote:
> Rein Klazes <wijn at wanadoo.nl> writes:
>
> > I managed to fixed it in two ways:
> >
> > 1. put a
> > X11DRV_CoerceDIBSection( physDevDst, DIB_Status_InSync, FALSE );
> > at the end of X11DRV_BitBlt. This probably defeats the whole purpose of
> > these protections so:
> >
> > 2. Add a "IsBadReadPtr( buffer, bytesToWrite)" in the top of WriteFile
> > to force an exception and everything works.
> >
> > Would that be an acceptable fix?
>
> We don't want that at the top of WriteFile, but it could be OK to add
> special handling of the INVALID_USER_BUFFER error, with a big FIXME
> comment...
Special handling: try again after an IsBadReadPtr call.
Changelog:
dlls/kernel : file.c
Work around a problem where WriteFile is asked to write memory protected
by DIBSection code.
Rein.
-------------- next part --------------
--- wine/dlls/kernel/file.c 2005-04-01 13:31:42.000000000 +0200
+++ mywine/dlls/kernel/file.c 2005-05-08 19:43:38.000000000 +0200
@@ -431,6 +431,7 @@ BOOL WINAPI WriteFile( HANDLE hFile, LPC
NTSTATUS status;
IO_STATUS_BLOCK iosb;
PIO_STATUS_BLOCK piosb = &iosb;
+ int FIUBflag = 0; /* Failed Invalid User Buffer flag */
TRACE("%p %p %ld %p %p\n", hFile, buffer, bytesToWrite, bytesWritten, overlapped );
@@ -448,8 +449,18 @@ BOOL WINAPI WriteFile( HANDLE hFile, LPC
piosb->u.Status = STATUS_PENDING;
piosb->Information = 0;
- status = NtWriteFile(hFile, hEvent, NULL, NULL, piosb,
- buffer, bytesToWrite, poffset, NULL);
+ while(1)
+ {
+ status = NtWriteFile(hFile, hEvent, NULL, NULL, piosb,
+ buffer, bytesToWrite, poffset, NULL);
+ if( status != STATUS_INVALID_USER_BUFFER || FIUBflag)
+ break;
+ FIUBflag = 1;
+ /* NtWriteFile does not always cause page faults, generate them now */
+ IsBadReadPtr( buffer, bytesToWrite);
+ }
+ if( FIUBflag && !status) /* failed first, but succeeded after access */
+ FIXME("Could not access memory (%p,%ld) at first, now OK. Protected by DIBSection code?\n", buffer, bytesToWrite);
if (status != STATUS_PENDING && bytesWritten)
*bytesWritten = piosb->Information;
More information about the wine-devel
mailing list