Jacek Caban : wineconsole: Use OVERLAPPED to wait for console events.

Alexandre Julliard julliard at winehq.org
Wed Jul 8 15:34:36 CDT 2020


Module: wine
Branch: master
Commit: 340a661723eab4afe2204837716e2b53cc14f5f2
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=340a661723eab4afe2204837716e2b53cc14f5f2

Author: Jacek Caban <jacek at codeweavers.com>
Date:   Wed Jul  8 16:31:55 2020 +0200

wineconsole: Use OVERLAPPED to wait for console events.

Signed-off-by: Jacek Caban <jacek at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 programs/wineconsole/curses.c          |  2 +-
 programs/wineconsole/user.c            |  2 +-
 programs/wineconsole/winecon_private.h |  4 ++++
 programs/wineconsole/wineconsole.c     | 18 +++++++++++++-----
 4 files changed, 19 insertions(+), 7 deletions(-)

diff --git a/programs/wineconsole/curses.c b/programs/wineconsole/curses.c
index 6fa669d150..ff38bafe2c 100644
--- a/programs/wineconsole/curses.c
+++ b/programs/wineconsole/curses.c
@@ -1020,7 +1020,7 @@ static int WCCURSES_MainLoop(struct inner_data* data)
     if (pipe( PRIVATE(data)->sync_pipe ) == -1) return 1;
     PRIVATE(data)->input_thread = CreateThread( NULL, 0, input_thread, data, 0, &id );
 
-    while (!data->dying && WaitForSingleObject(data->hSynchro, INFINITE) == WAIT_OBJECT_0)
+    while (!data->dying && WaitForSingleObject(data->overlapped.hEvent, INFINITE) == WAIT_OBJECT_0)
     {
         EnterCriticalSection(&PRIVATE(data)->lock);
         WINECON_GrabChanges(data);
diff --git a/programs/wineconsole/user.c b/programs/wineconsole/user.c
index de3f4ae98c..67531c0045 100644
--- a/programs/wineconsole/user.c
+++ b/programs/wineconsole/user.c
@@ -1365,7 +1365,7 @@ static int WCUSER_MainLoop(struct inner_data* data)
     ShowWindow(data->hWnd, data->nCmdShow);
     while (!data->dying || !data->curcfg.exit_on_die)
     {
-	switch (MsgWaitForMultipleObjects(1, &data->hSynchro, FALSE, INFINITE, QS_ALLINPUT))
+	switch (MsgWaitForMultipleObjects(1, &data->overlapped.hEvent, FALSE, INFINITE, QS_ALLINPUT))
 	{
 	case WAIT_OBJECT_0:
 	    WINECON_GrabChanges(data);
diff --git a/programs/wineconsole/winecon_private.h b/programs/wineconsole/winecon_private.h
index 54d8782a2a..cdf05e9332 100644
--- a/programs/wineconsole/winecon_private.h
+++ b/programs/wineconsole/winecon_private.h
@@ -22,6 +22,7 @@
 #include <windef.h>
 #include <winbase.h>
 #include <wincon.h>
+#include <wine/condrv.h>
 
 #include "wineconsole_res.h"
 
@@ -69,6 +70,9 @@ struct inner_data {
     BOOL                in_grab_changes;/* to handle re-entrant calls to WINECON_GrabChanges */
     BOOL                dying;          /* to TRUE when we've been notified by server that child has died */
 
+    OVERLAPPED          overlapped;
+    struct condrv_renderer_event events[256];
+
     int			(*fnMainLoop)(struct inner_data* data);
     void		(*fnPosCursor)(const struct inner_data* data);
     void		(*fnShapeCursor)(struct inner_data* data, int size, int vis, BOOL force);
diff --git a/programs/wineconsole/wineconsole.c b/programs/wineconsole/wineconsole.c
index bc2aef847e..6ccba13c8a 100644
--- a/programs/wineconsole/wineconsole.c
+++ b/programs/wineconsole/wineconsole.c
@@ -27,7 +27,6 @@
 #include "winecon_private.h"
 #include "winnls.h"
 #include "winuser.h"
-#include "wine/condrv.h"
 #include "wine/unicode.h"
 #include "wine/debug.h"
 
@@ -242,21 +241,20 @@ static void WINECON_SetColors(struct inner_data *data, const struct config_data*
  */
 void	WINECON_GrabChanges(struct inner_data* data)
 {
-    struct condrv_renderer_event evts[256];
+    struct condrv_renderer_event *evts = data->events;
     int i, ev_found;
     DWORD num;
     HANDLE h;
 
     if (data->in_grab_changes) return;
 
-    if (!DeviceIoControl( data->hSynchro, IOCTL_CONDRV_GET_RENDERER_EVENTS, NULL, 0, evts,
-                          sizeof(evts), &num, NULL ) || !num)
+    if (!GetOverlappedResult(data->hSynchro, &data->overlapped, &num, FALSE))
     {
         ERR( "failed to get renderer events: %u\n", GetLastError() );
         data->dying = TRUE;
         return;
     }
-    num /= sizeof(*evts);
+    num /= sizeof(data->events[0]);
     WINE_TRACE( "got %u events\n", num );
 
     /* FIXME: should do some event compression here (cursor pos, update) */
@@ -400,6 +398,13 @@ void	WINECON_GrabChanges(struct inner_data* data)
 	}
     }
     data->in_grab_changes = FALSE;
+
+    if (!DeviceIoControl(data->hSynchro, IOCTL_CONDRV_GET_RENDERER_EVENTS, NULL, 0, data->events,
+                         sizeof(data->events), NULL, &data->overlapped) && GetLastError() != ERROR_IO_PENDING)
+    {
+        ERR("failed to get renderer events: %u\n", GetLastError());
+        data->dying = TRUE;
+    }
 }
 
 /******************************************************************
@@ -590,6 +595,7 @@ static void WINECON_Delete(struct inner_data* data)
     if (data->hConOut)		CloseHandle(data->hConOut);
     if (data->hSynchro)		CloseHandle(data->hSynchro);
     if (data->hProcess)         CloseHandle(data->hProcess);
+    if (data->overlapped.hEvent) CloseHandle(data->overlapped.hEvent);
     HeapFree(GetProcessHeap(), 0, data->curcfg.registry);
     HeapFree(GetProcessHeap(), 0, data->cells);
     HeapFree(GetProcessHeap(), 0, data);
@@ -676,6 +682,8 @@ static struct inner_data* WINECON_Init(HINSTANCE hInst, DWORD pid, LPCWSTR appna
         /* should always be defined */
     }
 
+    if (!(data->overlapped.hEvent = CreateEventW(NULL, TRUE, TRUE, NULL))) goto error;
+
     /* the handles here are created without the whistles and bells required by console
      * (mainly because wineconsole doesn't need it)
      * - they are not inheritable




More information about the wine-cvs mailing list