Fix Timeout issue when terminating training on Windows

This commit is contained in:
torzdf 2019-06-23 19:37:04 +01:00
parent 0a83d9fb79
commit 19f97a53e5
3 changed files with 31 additions and 18 deletions

View File

@ -4,7 +4,7 @@ import os
import logging
import re
import signal
from subprocess import PIPE, Popen, TimeoutExpired
from subprocess import PIPE, Popen
import sys
from threading import Thread
from time import time
@ -13,6 +13,10 @@ import psutil
from .utils import get_config, get_images
if os.name == "nt":
import win32console
logger = logging.getLogger(__name__) # pylint: disable=invalid-name
@ -332,28 +336,36 @@ class FaceswapControl():
timeout = get_config().tk_vars["traintimeout"].get()
logger.debug("Sending Exit Signal")
print("Sending Exit Signal", flush=True)
now = time()
if os.name == "nt":
try:
logger.debug("Sending carriage return to process")
self.process.communicate(input="\n", timeout=timeout)
except TimeoutExpired:
logger.error("Timeout reached sending Exit Signal")
self.terminate_all_children()
logger.debug("Sending carriage return to process")
con_in = win32console.GetStdHandle( # pylint:disable=c-extension-no-member
win32console.STD_INPUT_HANDLE) # pylint:disable=c-extension-no-member
keypress = self.generate_windows_keypress("\n")
con_in.WriteConsoleInput([keypress])
else:
logger.debug("Sending SIGINT to process")
now = time()
self.process.send_signal(signal.SIGINT)
while True:
timeelapsed = time() - now
if self.process.poll() is not None:
break
if timeelapsed > timeout:
logger.error("Timeout reached sending Exit Signal")
self.terminate_all_children()
return
while True:
timeelapsed = time() - now
if self.process.poll() is not None:
break
if timeelapsed > timeout:
logger.error("Timeout reached sending Exit Signal")
self.terminate_all_children()
else:
self.terminate_all_children()
@staticmethod
def generate_windows_keypress(character):
""" Generate an 'Enter' keypress to terminate Windows training """
buf = win32console.PyINPUT_RECORDType( # pylint:disable=c-extension-no-member
win32console.KEY_EVENT) # pylint:disable=c-extension-no-member
buf.KeyDown = 1
buf.RepeatCount = 1
buf.Char = character
return buf
@staticmethod
def terminate_all_children():
""" Terminates all children """

View File

@ -59,7 +59,7 @@ class KBHit:
def getch(self):
""" Returns a keyboard character after kbhit() has been called.
Should not be called in the same program as getarrow(). """
if self.is_gui:
if self.is_gui and os.name != "nt":
return None
if os.name == "nt":
return msvcrt.getch().decode("utf-8")
@ -87,7 +87,7 @@ class KBHit:
def kbhit(self):
""" Returns True if keyboard character was hit, False otherwise. """
if self.is_gui:
if self.is_gui and os.name != "nt":
return None
if os.name == "nt":
return msvcrt.kbhit()

View File

@ -15,6 +15,7 @@ ffmpy==0.2.2
nvidia-ml-py3
h5py==2.9.0
Keras==2.2.4
pywin32 ; sys_platform == "win32"
# tensorflow is included within the docker image.
# If you are looking for dependencies for a manual install,