"Cihan" == Cihan Altinay cihan@uq.edu.au writes:
Cihan> Hi, I am trying to get G-Ware[1] to run under wine which provides Cihan> a user interface to set up Echo Canceller Units made by Cihan> ClearOne. The unit is connected to the serial port (com1 = Cihan> ttyS0). The only way I can start the program at all is by Cihan> configuring wine to act as Windows 95/98 and using native COM Cihan> dll's. Furthermore, 'GWare.exe' starts 'PSRServe.exe' under Cihan> native Windows but not under wine so I do the following in a bash Cihan> file: wine C:\Program\ Files\G-Ware\PSRServe.exe & wine Cihan> C:\Program\ Files\G-Ware\GWare.exe
Cihan> When I connect to the device I get endless
Cihan> fixme:comm:COMM_WaitCommEvent EV_RXFLAG not handled
Cihan> messages before communication breaks with this:
Cihan> wine client error:3bc: pipe: Too many open files
Cihan> After investigating I found out that indeed the number of open Cihan> pipes to ttyS0 increases statically so I tried to find the reason Cihan> and suspect the following (using the CVS checkout from 20051102):
Cihan> In the function COMM_WaitCommEvent in /dlls/kernel/comm.c line Cihan> 2106 a thread is created for WaitCommEventService. However, in Cihan> this branch of the if-statement fd is not released (using Cihan> release_comm_fd). Releasing fd seems to work and the number of Cihan> open pipes don't get past 200-300.
I wrote the WaitComEvent code. Probably release_comm_fd( commio->handle, fd ); HeapFree(GetProcessHeap(), 0, commio ); needs to be executed for both cases. I am just compiling and testing...
Cihan> I am new to wine development and this is just a guess and I might Cihan> be totally wrong. Unfortunately this does not fix the Cihan> communication with the device (It reports timeouts and errors Cihan> retrieving values etc). I guess this has to do with the first Cihan> fixme messages I mentioned. Can anybody tell me what EV_RXFLAG Cihan> is used for?
Google->WaitCommEvent->msdn.microsoft.com/library/en-us/devio/base/waitcommevent.asp -> Look under lpEventMask
The program wants to be informed, when the device has sent an Event char. I don't know about a way to do this in libc/kernel way in Unix. Actually the only way I see is by polling the serial port andd checking for the event character in our serial line service thread. Probably more places in the comm code need to care for the Event character (the DCB structure e.g)
Cihan> Using WINEDEBUG=+tid,+comm I compared the output to Cihan> what Sysinternals PortMon[2] gives me on native Windows and it Cihan> really looks promising. Is there a way to display the actual data Cihan> that was sent/received through the serial port? I tried Cihan> WINEDEBUG=+io which does not work.
Sending/receiving is done via kernel/file.c Following patch traces all write/reads, so you have to manually look for those on the serial line. retrieving revision 1.40 diff -u -w -r1.40 file.c --- wine/dlls/kernel/file.c 11 Jul 2005 14:23:46 -0000 1.40 +++ wine/dlls/kernel/file.c 5 Sep 2005 08:25:54 -0000 @@ -46,6 +46,7 @@ #include "wine/server.h"
WINE_DEFAULT_DEBUG_CHANNEL(file); +WINE_DECLARE_DEBUG_CHANNEL(fileio);
HANDLE dos_handles[DOS_TABLE_SIZE];
@@ -377,6 +378,15 @@ if (status != STATUS_PENDING && bytesRead) *bytesRead = io_status->Information;
+ if (TRACE_ON(fileio) && bytesRead && *bytesRead) + { + int i; + DPRINTF("ReadFile %9ld Bytes from %p: 0x", *bytesRead, hFile); + for(i=0; i<*bytesRead && i<20; i++) + DPRINTF("%02x",((unsigned char*)buffer)[i]); + DPRINTF(" %s\n",debugstr_an((unsigned char*)buffer,(*bytesRead>20)?20:*bytesRead)); + } + if (status && status != STATUS_END_OF_FILE && status != STATUS_TIMEOUT) { SetLastError( RtlNtStatusToDosError(status) ); @@ -433,6 +443,15 @@
TRACE("%p %p %ld %p %p\n", hFile, buffer, bytesToWrite, bytesWritten, overlapped );
+ if (TRACE_ON(fileio) && bytesToWrite) + { + int i; + DPRINTF("WriteFile %8ld Bytes from %p: 0x", bytesToWrite, hFile); + for(i=0; i<bytesToWrite && i<20; i++) + DPRINTF("%02x",((unsigned char*)buffer)[i]); + DPRINTF(" %s\n",debugstr_an(buffer,(bytesToWrite>20)?20:bytesToWrite)); + } + if (is_console_handle(hFile)) return WriteConsoleA(hFile, buffer, bytesToWrite, bytesWritten, NULL);