summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKostis Anagnostopoulos <ankostis@gmail.com>2016-09-26 01:36:57 +0200
committerKostis Anagnostopoulos <ankostis@gmail.com>2016-09-26 13:37:55 +0200
commit7ec2f8a4f26cec3fbbe1fb447058acaf508b39c0 (patch)
tree2868007d4c4be16ee5e24ca09df6ab2533dea248
parent082851e0afd3a58790fe3c2434f6d070f97c69c1 (diff)
downloadgitpython-7ec2f8a4f26cec3fbbe1fb447058acaf508b39c0.tar.gz
apveyor, #519: FIX incomplete Popen pump
+ The code in `_read_lines_from_fno()` was reading the stream only once per invocation, so when input was larger than `mmap.PAGESIZE`, bytes were forgotten in the stream. + Replaced buffer-building code with iterate-on-file-descriptors. + Also set deamon-threads.
-rw-r--r--git/cmd.py16
-rw-r--r--git/test/test_git.py8
2 files changed, 18 insertions, 6 deletions
diff --git a/git/cmd.py b/git/cmd.py
index 1cc656bf..c700d7a4 100644
--- a/git/cmd.py
+++ b/git/cmd.py
@@ -193,14 +193,24 @@ def handle_process_output(process, stdout_handler, stderr_handler, finalizer):
else:
# Oh ... probably we are on windows. select.select() can only handle sockets, we have files
# The only reliable way to do this now is to use threads and wait for both to finish
+ def _handle_lines(fd, handler, wg):
+ for line in fd:
+ line = line.decode(defenc)
+ if line and handler:
+ handler(line)
+ if wg:
+ wg.done()
+
# Since the finalizer is expected to wait, we don't have to introduce our own wait primitive
# NO: It's not enough unfortunately, and we will have to sync the threads
wg = WaitGroup()
- for fno, (handler, buf_list) in fdmap.items():
+ for fd, handler in zip((process.stdout, process.stderr),
+ (stdout_handler, stderr_handler)):
wg.add(1)
- t = threading.Thread(target=lambda: _deplete_buffer(fno, handler, buf_list, wg))
+ t = threading.Thread(target=_handle_lines, args=(fd, handler, wg))
+ t.setDaemon(True)
t.start()
- # end
+
# NOTE: Just joining threads can possibly fail as there is a gap between .start() and when it's
# actually started, which could make the wait() call to just return because the thread is not yet
# active
diff --git a/git/test/test_git.py b/git/test/test_git.py
index 534539d7..82ed2ace 100644
--- a/git/test/test_git.py
+++ b/git/test/test_git.py
@@ -238,9 +238,11 @@ class TestGit(TestBase):
stdin=None,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
- shell=False)
+ shell=False,
+ creationflags=Git.CREATE_NO_WINDOW if sys.platform == 'win32' else 0,
+ )
handle_process_output(proc, counter_stdout, counter_stderr, lambda proc: proc.wait())
- assert count[1] == line_count
- assert count[2] == line_count
+ self.assertEqual(count[1], line_count)
+ self.assertEqual(count[2], line_count)