Skip to content

Commit

Permalink
[utils] Fix _windows_write_string (Fixes #2779)
Browse files Browse the repository at this point in the history
It turns out that the function did not work for outputs longer than 1024 UCS-2 tokens.
Write non-BMP characters one by one to ensure that we count correctly.
  • Loading branch information
phihag committed Apr 21, 2014
1 parent edec83a commit d1b9c91
Showing 1 changed file with 16 additions and 7 deletions.
23 changes: 16 additions & 7 deletions youtube_dl/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -923,9 +923,6 @@ def _windows_write_string(s, out):
2: -12,
}

def ucs2_len(s):
return sum((2 if ord(c) > 0xffff else 1) for c in s)

fileno = out.fileno()
if fileno not in WIN_OUTPUT_IDS:
return False
Expand Down Expand Up @@ -959,13 +956,25 @@ def not_a_console(handle):
if not_a_console(h):
return False

remaining = ucs2_len(s)
while remaining > 0:
def next_nonbmp_pos(s):
try:
return next(i for i, c in enumerate(s) if ord(c) > 0xffff)
except StopIteration:
return len(s)

while s:
count = min(next_nonbmp_pos(s), 1024)

ret = WriteConsoleW(
h, s, min(remaining, 1024), ctypes.byref(written), None)
h, s, count if count else 2, ctypes.byref(written), None)
if ret == 0:
raise OSError('Failed to write string')
remaining -= written.value
if not count: # We just wrote a non-BMP character
assert written.value == 2
s = s[1:]
else:
assert written.value > 0
s = s[written.value:]
return True


Expand Down

0 comments on commit d1b9c91

Please sign in to comment.