Commit 2f20c249 authored by Guido van Rossum's avatar Guido van Rossum

Fixed the EventHook() code so that it also works on Windows, sort of.

(The "sort of" is because it uses kbhit() to detect that the user
starts typing, and then no events are processed until they hit
return.)

Also fixed a nasty locking bug: EventHook() is called without the Tcl
lock set, so it can't use the ENTER_PYTHON and LEAVE_PYTHON macros,
which manipulate both the Python and the Tcl lock.  I now only acquire
and release the Python lock.

(Haven't tested this on Unix yet...)
parent 175157a7
...@@ -121,6 +121,11 @@ PERFORMANCE OF THIS SOFTWARE. ...@@ -121,6 +121,11 @@ PERFORMANCE OF THIS SOFTWARE.
#endif /* HAVE_CREATEFILEHANDLER */ #endif /* HAVE_CREATEFILEHANDLER */
#ifdef MS_WINDOWS
#include <conio.h>
#define WAIT_FOR_STDIN
#endif
#ifdef WITH_THREAD #ifdef WITH_THREAD
/* The threading situation is complicated. Tcl is not thread-safe, except for /* The threading situation is complicated. Tcl is not thread-safe, except for
...@@ -1822,6 +1827,7 @@ static PyMethodDef moduleMethods[] = ...@@ -1822,6 +1827,7 @@ static PyMethodDef moduleMethods[] =
static int stdin_ready = 0; static int stdin_ready = 0;
#ifndef MS_WINDOWS
static void static void
MyFileProc(clientData, mask) MyFileProc(clientData, mask)
void *clientData; void *clientData;
...@@ -1829,22 +1835,34 @@ MyFileProc(clientData, mask) ...@@ -1829,22 +1835,34 @@ MyFileProc(clientData, mask)
{ {
stdin_ready = 1; stdin_ready = 1;
} }
#endif
static PyThreadState *event_tstate = NULL; static PyThreadState *event_tstate = NULL;
static int static int
EventHook() EventHook()
{ {
#ifndef MS_WINDOWS
FHANDLE tfile; FHANDLE tfile;
#endif
ENTER_PYTHON(event_tstate) if (PyThreadState_Swap(NULL) != NULL)
tfile = MAKEFHANDLE(fileno(stdin)); Py_FatalError("EventHook with non-NULL tstate\n");
PyEval_RestoreThread(event_tstate);
stdin_ready = 0; stdin_ready = 0;
errorInCmd = 0;
#ifndef MS_WINDOWS
tfile = MAKEFHANDLE(fileno(stdin));
Tcl_CreateFileHandler(tfile, TCL_READABLE, MyFileProc, NULL); Tcl_CreateFileHandler(tfile, TCL_READABLE, MyFileProc, NULL);
#endif
while (!errorInCmd && !stdin_ready) { while (!errorInCmd && !stdin_ready) {
int result; int result;
#ifdef MS_WINDOWS
#ifdef WITH_THREAD if (_kbhit()) {
stdin_ready = 1;
break;
}
#endif
#if defined(WITH_THREAD) || defined(MS_WINDOWS)
ENTER_TCL ENTER_TCL
result = Tcl_DoOneEvent(TCL_DONT_WAIT); result = Tcl_DoOneEvent(TCL_DONT_WAIT);
release_lock(tcl_lock); release_lock(tcl_lock);
...@@ -1858,14 +1876,16 @@ EventHook() ...@@ -1858,14 +1876,16 @@ EventHook()
if (result < 0) if (result < 0)
break; break;
} }
#ifndef MS_WINDOWS
Tcl_DeleteFileHandler(tfile); Tcl_DeleteFileHandler(tfile);
#endif
if (errorInCmd) { if (errorInCmd) {
errorInCmd = 0; errorInCmd = 0;
PyErr_Restore(excInCmd, valInCmd, trbInCmd); PyErr_Restore(excInCmd, valInCmd, trbInCmd);
excInCmd = valInCmd = trbInCmd = NULL; excInCmd = valInCmd = trbInCmd = NULL;
PyErr_Print(); PyErr_Print();
} }
LEAVE_PYTHON PyEval_SaveThread();
return 0; return 0;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment