summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRichard Purdie <richard.purdie@linuxfoundation.org>2017-01-04 23:23:52 (GMT)
committerRichard Purdie <richard.purdie@linuxfoundation.org>2017-01-05 13:54:07 (GMT)
commit9f6a1043f68580ed9604e750fd0f993f933bb66e (patch)
treecad95efa0bb8893159252cb2180c6c6a66d1d9e8
parent3c9b1febc4840cd1b7d6784076d61efe8e87271f (diff)
downloadpoky-9f6a1043f68580ed9604e750fd0f993f933bb66e.tar.gz
bitbake: prserv/serv: Tweak stdout manipulation to be stream safe
We've been seeing oe-selftest failures under puzzling circumstances. It turns out if you run oe-selftest on a machine with xmlrunner installed and have the recent tinfoil2 changes, the launching of PR server crashes leading to selftest hanging if using an autoloaded PR server. The reason is that xmlrunner uses an io.StringIO object as stdout/stderr instead of the usual io.TextIOWrapper and StringIO lacks a fileno() method. We have to deal with both cases and in the python way, we try and then seek forgivness if we see an AttributeError or UnSupportedOperation exception. Unfortunately we have to deal with both cases as we may be performing a traditiional double fork() from the commandline, or a larger python program. [YOCTO #10866] (Bitbake rev: 26243f04e3af652291d13e85c084057104fe155b) Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
-rw-r--r--bitbake/lib/prserv/serv.py21
1 files changed, 17 insertions, 4 deletions
diff --git a/bitbake/lib/prserv/serv.py b/bitbake/lib/prserv/serv.py
index 350b085..d9b602f 100644
--- a/bitbake/lib/prserv/serv.py
+++ b/bitbake/lib/prserv/serv.py
@@ -242,12 +242,25 @@ class PRServer(SimpleXMLRPCServer):
242 242
243 sys.stdout.flush() 243 sys.stdout.flush()
244 sys.stderr.flush() 244 sys.stderr.flush()
245
246 # We could be called from a python thread with io.StringIO as
247 # stdout/stderr or it could be 'real' unix fd forking where we need
248 # to physically close the fds to prevent the program launching us from
249 # potentially hanging on a pipe. Handle both cases.
245 si = open('/dev/null', 'r') 250 si = open('/dev/null', 'r')
251 try:
252 os.dup2(si.fileno(),sys.stdin.fileno())
253 except (AttributeError, io.UnsupportedOperation):
254 sys.stdin = si
246 so = open(self.logfile, 'a+') 255 so = open(self.logfile, 'a+')
247 se = so 256 try:
248 os.dup2(si.fileno(),sys.stdin.fileno()) 257 os.dup2(so.fileno(),sys.stdout.fileno())
249 os.dup2(so.fileno(),sys.stdout.fileno()) 258 except (AttributeError, io.UnsupportedOperation):
250 os.dup2(se.fileno(),sys.stderr.fileno()) 259 sys.stdout = so
260 try:
261 os.dup2(so.fileno(),sys.stderr.fileno())
262 except (AttributeError, io.UnsupportedOperation):
263 sys.stderr = so
251 264
252 # Clear out all log handlers prior to the fork() to avoid calling 265 # Clear out all log handlers prior to the fork() to avoid calling
253 # event handlers not part of the PRserver 266 # event handlers not part of the PRserver