[Bug 35991] WinProladder v3.23 crashes during 'PLC connect check' (async event poll worker writes to user event mask buffer whose lifetime is limited)

wine-bugs at winehq.org wine-bugs at winehq.org
Mon Apr 14 09:11:37 CDT 2014


http://bugs.winehq.org/show_bug.cgi?id=35991

Anastasius Focht <focht at gmx.net> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|UNCONFIRMED                 |NEW
                 CC|                            |focht at gmx.net
            Summary|Communication via COM1      |WinProladder v3.23 crashes
                   |crashes Fatek WinProladder  |during 'PLC connect check'
                   |                            |(async event poll worker
                   |                            |writes to user event mask
                   |                            |buffer whose lifetime is
                   |                            |limited)
     Ever confirmed|0                           |1

--- Comment #5 from Anastasius Focht <focht at gmx.net> ---
Hello folks,

confirming.

Can be reproduced without actual device, you just need a serial port
(USB-to-serial adapter).

Create the dosdevice symlink (COM1) and have the app doing the scan the port
using different baud rates/settings.

--- snip ---
$ pwd
/home/focht/.wine/drive_c/Program Files/Fatek/WinProladder

$ WINEDEBUG=+tid,+seh,+loaddll,+process,+comm,+ntdll,+relay wine ./WProlad.exe
>>log.txt 2>&1
...
003f:Starting thread proc 0x40004a60 (arg=0xcd6e50)
003f:Call KERNEL32.CreateEventA(00000000,ffffffff,ffffffff,00000000)
ret=0038c151
003f:Ret  KERNEL32.CreateEventA() retval=000000e0 ret=0038c151
003f:Call KERNEL32.CreateEventA(00000000,ffffffff,ffffffff,00000000)
ret=0038c17a
003f:Ret  KERNEL32.CreateEventA() retval=000000e4 ret=0038c17a
003f:Call KERNEL32.SetCommMask(000000d0,000001a1) ret=0038c1cb
003f:trace:comm:SetCommMask handle 0xd0, mask 1a1
003f:trace:ntdll:NtDeviceIoControlFile
(0xd0,(nil),(nil),(nil),0x21be0f0,0x001b0044,0x21be1a4,0x00000004,(nil),0x00000000)
003f:trace:comm:io_control 0xd0 IOCTL_SERIAL_SET_WAIT_MASK 0x21be1a4 4 (nil) 0
0x21be0f0
003f:Ret  KERNEL32.SetCommMask() retval=00000001 ret=0038c1cb
003f:Call KERNEL32.WaitForSingleObject(000000d4,00000000) ret=0038c47d
003f:Ret  KERNEL32.WaitForSingleObject() retval=00000102 ret=0038c47d
003f:Call KERNEL32.WaitCommEvent(000000d0,021bea14,021be1e0) ret=0038c498
003f:trace:ntdll:NtDeviceIoControlFile
(0xd0,0xe4,(nil),0x21be1e0,0x21be1e0,0x001b0048,(nil),0x00000000,0x21bea14,0x00000004)
003f:trace:comm:io_control 0xd0 IOCTL_SERIAL_WAIT_ON_MASK (nil) 0 0x21bea14 4
0x21be1e0
003f:trace:comm:wait_on commio=0x1a0f0d8, commio->events=0x1100b8
003f:trace:comm:get_irq_info TIOCGICOUNT err Inappropriate ioctl for device
003f:trace:comm:get_irq_info TIOCSERGETLSR err Inappropriate ioctl for device
003f:trace:comm:get_modem_status 0004 -> 
003f:trace:comm:check_events mask 0x000001a1
003f:trace:comm:check_events old->rx          0x00000000 vs. new->rx         
0x00000000
003f:trace:comm:check_events old->tx          0x00000000 vs. new->tx         
0x00000000
003f:trace:comm:check_events old->frame       0x00000000 vs. new->frame      
0x00000000
003f:trace:comm:check_events old->overrun     0x00000000 vs. new->overrun    
0x00000000
003f:trace:comm:check_events old->parity      0x00000000 vs. new->parity     
0x00000000
003f:trace:comm:check_events old->brk         0x00000000 vs. new->brk        
0x00000000
003f:trace:comm:check_events old->buf_overrun 0x00000000 vs. new->buf_overrun
0x00000000
003f:trace:comm:check_events old->temt        0x00000001 vs. new->temt       
0x00000001
003f:Ret  KERNEL32.WaitCommEvent() retval=00000000 ret=0038c498
0026:trace:comm:wait_for_event commio=0x1a0f0d8 device=0xd0 fd=0x0000000f
mask=0x000001a1 buffer=0x21bea14 event=0xe4 irq_info=0x1a0f0f8
003f:Call KERNEL32.GetLastError() ret=0038c4b6
003f:Ret  KERNEL32.GetLastError() retval=000003e5 ret=0038c4b6
003f:Call KERNEL32.WaitForSingleObject(000000d4,00000000) ret=0038c31d
003f:Ret  KERNEL32.WaitForSingleObject() retval=00000102 ret=0038c31d
003f:Call KERNEL32.ReadFile(000000d0,021be214,00000800,021bea1c,021be1f4)
ret=0038c340
003f:trace:ntdll:NtReadFile
(0xd0,0xe0,(nil),0x21be1f4,0x21be1f4,0x21be214,0x00000800,0x21be110,(nil)),partial
stub!
003f:trace:ntdll:NtDeviceIoControlFile
(0xd0,(nil),(nil),(nil),0x21bdf40,0x001b0020,(nil),0x00000000,0x21bdf48,0x00000014)
003f:trace:comm:io_control 0xd0 IOCTL_SERIAL_GET_TIMEOUTS (nil) 0 0x21bdf48 20
0x21bdf40
003f:trace:ntdll:NtReadFile = 0x00000103
003f:Ret  KERNEL32.ReadFile() retval=00000000 ret=0038c340
003f:Call KERNEL32.GetLastError() ret=0038c35f
003f:Ret  KERNEL32.GetLastError() retval=000003e5 ret=0038c35f
003f:Call KERNEL32.WaitForMultipleObjects(00000003,021be208,00000000,ffffffff)
ret=0038c22c
0026:trace:comm:get_irq_info TIOCGICOUNT err Inappropriate ioctl for device
0026:trace:comm:get_irq_info TIOCSERGETLSR err Inappropriate ioctl for device
0026:trace:comm:get_modem_status 0004 -> 
0026:trace:comm:check_events mask 0x000001a1
0026:trace:comm:check_events old->rx          0x00000000 vs. new->rx         
0x00000000
0026:trace:comm:check_events old->tx          0x00000000 vs. new->tx         
0x00000000
0026:trace:comm:check_events old->frame       0x00000000 vs. new->frame      
0x00000000
0026:trace:comm:check_events old->overrun     0x00000000 vs. new->overrun    
0x00000000
0026:trace:comm:check_events old->parity      0x00000000 vs. new->parity     
0x00000000
0026:trace:comm:check_events old->brk         0x00000000 vs. new->brk        
0x00000000
0026:trace:comm:check_events old->buf_overrun 0x00000000 vs. new->buf_overrun
0x00000000
0026:trace:comm:check_events old->temt        0x00000001 vs. new->temt       
0x00000001
0026:trace:comm:get_irq_info TIOCGICOUNT err Inappropriate ioctl for device
0026:trace:comm:get_irq_info TIOCSERGETLSR err Inappropriate ioctl for device 
...
003f:Ret  KERNEL32.WaitForMultipleObjects() retval=00000000 ret=0038c22c
003f:Call KERNEL32.PurgeComm(000000d0,0000000a) ret=0038c2df
003f:trace:ntdll:NtDeviceIoControlFile
(0xd0,(nil),(nil),(nil),0x21be100,0x001b004c,0x21be1a4,0x00000004,(nil),0x00000000)
003f:trace:comm:io_control 0xd0 IOCTL_SERIAL_PURGE 0x21be1a4 4 (nil) 0
0x21be100
003f:Ret  KERNEL32.PurgeComm() retval=00000001 ret=0038c2df
003f:Call KERNEL32.CloseHandle(000000e0) ret=0038c2eb
003f:Ret  KERNEL32.CloseHandle() retval=00000001 ret=0038c2eb
003f:Call KERNEL32.CloseHandle(000000e4) ret=0038c2f7
003f:Ret  KERNEL32.CloseHandle() retval=00000001 ret=0038c2f7
003f:Call KERNEL32.ExitThread(00000000) ret=40004ae2 
...
0026:trace:comm:get_irq_info TIOCGICOUNT err Inappropriate ioctl for device
0026:trace:comm:get_irq_info TIOCSERGETLSR err Inappropriate ioctl for device
0026:trace:comm:get_modem_status 0004 -> 
0026:trace:comm:check_events mask 0x000001a1
0026:trace:comm:check_events old->rx          0x00000000 vs. new->rx         
0x00000000
0026:trace:comm:check_events old->tx          0x00000000 vs. new->tx         
0x00000000
0026:trace:comm:check_events old->frame       0x00000000 vs. new->frame      
0x00000000
0026:trace:comm:check_events old->overrun     0x00000000 vs. new->overrun    
0x00000000
0026:trace:comm:check_events old->parity      0x00000000 vs. new->parity     
0x00000000
0026:trace:comm:check_events old->brk         0x00000000 vs. new->brk        
0x00000000
0026:trace:comm:check_events old->buf_overrun 0x00000000 vs. new->buf_overrun
0x00000000
0026:trace:comm:check_events old->temt        0x00000001 vs. new->temt       
0x00000001
0026:trace:comm:get_irq_info TIOCGICOUNT err Inappropriate ioctl for device
0026:trace:comm:get_irq_info TIOCSERGETLSR err Bad file descriptor
0026:trace:comm:get_irq_info TIOCOUTQ err Bad file descriptor
0026:trace:ntdll:FILE_GetNtStatus errno = 9
0026:warn:comm:get_modem_status TIOCMGET err Bad file descriptor
0026:trace:ntdll:FILE_GetNtStatus errno = 9
0026:trace:comm:wait_for_event get_modem_status failed
0026:trace:seh:raise_exception code=c0000005 flags=0 addr=0x7bc7ee96
ip=7bc7ee96 tid=0026
0026:trace:seh:raise_exception  info[0]=00000001
0026:trace:seh:raise_exception  info[1]=021bea14
0026:trace:seh:raise_exception  eax=021bea14 ebx=7bcd2000 ecx=00000000
edx=022bef8c esi=00000000 edi=021bea14
0026:trace:seh:raise_exception  ebp=022be9d8 esp=022be920 cs=0023 ds=002b
es=002b fs=0063 gs=006b flags=00210206
0026:trace:seh:call_stack_handlers calling handler at 0x7bc9f9f7 code=c0000005
flags=0
0026:Call KERNEL32.UnhandledExceptionFilter(022be3f4) ret=7bc9fa31 
...
Unhandled exception: page fault on write access to 0x021bea14 in 32-bit code
(0x7bc7ee96).
Register dump:
 CS:0023 SS:002b DS:002b ES:002b FS:0063 GS:006b
 EIP:7bc7ee96 ESP:022be920 EBP:022be9d8 EFLAGS:00210206(  R- --  I   - -P- )
 EAX:021bea14 EBX:7bcd2000 ECX:00000000 EDX:022bef8c
 ESI:00000000 EDI:021bea14
...
Backtrace:
=>0 0x7bc7ee96 wait_for_event+0x1a2(arg=<couldn't compute location>)
[/home/focht/projects/wine/wine.repo/src/dlls/ntdll/serial.c:951] in ntdll
(0x022be9d8)
  1 0x7bc90e67 worker_thread_proc+0x14d(param=<couldn't compute location>)
[/home/focht/projects/wine/wine.repo/src/dlls/ntdll/threadpool.c:110] in ntdll
(0x022bea48)
  2 0x7bc87504 call_thread_func_wrapper+0xb() in ntdll (0x022bea68)
  3 0x7bc8754d call_thread_func+0x3e(entry=0x7bc90d19, arg=0x0(nil),
frame=0x22beb68)
[/home/focht/projects/wine/wine.repo/src/dlls/ntdll/signal_i386.c:2629] in
ntdll (0x022beb48)
  4 0x7bc874e2 call_thread_entry_point+0x11() in ntdll (0x022beb68)
  5 0x7bc8e92d start_thread+0x11a(info=0x7ffccfb8)
[/home/focht/projects/wine/wine.repo/src/dlls/ntdll/thread.c:428] in ntdll
(0x022bf3a8)
  6 0xf75ce9da start_thread+0xc9() in libpthread.so.0 (0x022bf468)
  7 0xf7500bfe __clone+0x5d() in libc.so.6 (0x00000000) 
...
0x7bc7ee96 wait_for_event+0x1a2
[/home/focht/projects/wine/wine.repo/src/dlls/ntdll/serial.c:951] in ntdll:
movl    $0x0,0x0(%eax)
951                    *commio->events = 0;
Modules:
Module    Address            Debug info    Name (116 modules)
PE      340000-  35a000    Deferred        fautil10.bpl
PE      360000-  380000    Deferred        faplcdb10.bpl
PE      380000-  3a2000    Deferred        fawin50.bpl
PE      3b0000-  3ba000    Deferred        famnode10.bpl
PE      3c0000-  3d5000    Deferred        futil
PE      400000-  846000    Deferred        wprolad
PE      850000-  a41000    Deferred        faiocfg10.bpl
PE      a50000-  bb1000    Deferred        prolad18
PE    32500000-32677000    Deferred        cc3250mt
PE    40000000-401f2000    Deferred        vcl50.bpl
PE    402f0000-40333000    Deferred        vclx50.bpl
PE    40b90000-40bc6000    Deferred        nmfast50.bpl
PE    41000000-4100c000    Deferred        borlndmm
ELF    4eb20000-4eb3d000    Deferred        libgcc_s.so.1
PE    50600000-50629000    Deferred        bcbsmp50.bpl
ELF    7b800000-7ba61000    Deferred        kernel32<elf>
  \-PE    7b810000-7ba61000    \               kernel32 
...
Threads:
process  tid      prio (all id:s are in hex)
...
00000022 (D) C:\Program Files\Fatek\WinProladder\WProlad.exe
    00000026    0 <==
    00000023    0 
--- snip ---

The app creates a reader thread which carries out the serial communication to
decouple/avoid blocking the user interface.
The reader thread calls 'WaitCommEvent' with a thread-stack based 'lpEvtMask'
buffer (out parameter).

WaitCommEvent() returns with ERROR_IO_PENDING (expected) and the thread issues
an overlapped ReadFile() which is waited on with WaitForMultipleObjects().

At one point the serial comm reader thread decides to give up, issues
PurgeComm(), closes the event handles (cleanup) and terminates itself.

Earlier, Wine created an async worker in IOCTL_SERIAL_WAIT_ON_MASK ioctl
handler using RtlQueueWorkItem(), which kicks off a poll routine in another
thread, see wait_on() here:

http://source.winehq.org/git/wine.git/blob/a890d0f030a864d893646bd0c29dd761781bcdd0:/dlls/ntdll/serial.c#l922

A short time later the async worker polling loop figures out something is wrong
('get_modem_status' failed) and writes zero to the user-supplied event mask
buffer.

This causes the crash because the original reader thread already terminated at
that point and the buffer (thread stack variable) is no longer accessible ->
*boom*

$ sha1sum Wprolad323-17205-1-ENU.exe 
9491cb2a0fdc745594a30d2025c89b7c38f6b9ca  Wprolad323-17205-1-ENU.exe

$ du -sh Wprolad323-17205-1-ENU.exe 
3.2M    Wprolad323-17205-1-ENU.exe

$ wine --version
wine-1.7.16-134-g0ff879b

Regards

-- 
Do not reply to this email, post in Bugzilla using the
above URL to reply.
You are receiving this mail because:
You are watching all bug changes.



More information about the wine-bugs mailing list