| OLD | NEW |
| 1 # Copyright (C) 2011 Google Inc. All rights reserved. | 1 # Copyright (C) 2011 Google Inc. All rights reserved. |
| 2 # | 2 # |
| 3 # Redistribution and use in source and binary forms, with or without | 3 # Redistribution and use in source and binary forms, with or without |
| 4 # modification, are permitted provided that the following conditions are | 4 # modification, are permitted provided that the following conditions are |
| 5 # met: | 5 # met: |
| 6 # | 6 # |
| 7 # * Redistributions of source code must retain the above copyright | 7 # * Redistributions of source code must retain the above copyright |
| 8 # notice, this list of conditions and the following disclaimer. | 8 # notice, this list of conditions and the following disclaimer. |
| 9 # * Redistributions in binary form must reproduce the above | 9 # * Redistributions in binary form must reproduce the above |
| 10 # copyright notice, this list of conditions and the following disclaimer | 10 # copyright notice, this list of conditions and the following disclaimer |
| (...skipping 20 matching lines...) Expand all Loading... |
| 31 import logging | 31 import logging |
| 32 import re | 32 import re |
| 33 import shlex | 33 import shlex |
| 34 import sys | 34 import sys |
| 35 import time | 35 import time |
| 36 import os | 36 import os |
| 37 | 37 |
| 38 from webkitpy.common.system import path | 38 from webkitpy.common.system import path |
| 39 from webkitpy.common.system.profiler import ProfilerFactory | 39 from webkitpy.common.system.profiler import ProfilerFactory |
| 40 | 40 |
| 41 | |
| 42 _log = logging.getLogger(__name__) | 41 _log = logging.getLogger(__name__) |
| 43 | 42 |
| 44 | |
| 45 DRIVER_START_TIMEOUT_SECS = 30 | 43 DRIVER_START_TIMEOUT_SECS = 30 |
| 46 | 44 |
| 47 | 45 |
| 48 class DriverInput(object): | 46 class DriverInput(object): |
| 49 def __init__(self, test_name, timeout, image_hash, should_run_pixel_test, ar
gs): | 47 def __init__(self, test_name, timeout, image_hash, should_run_pixel_test, ar
gs): |
| 50 self.test_name = test_name | 48 self.test_name = test_name |
| 51 self.timeout = timeout # in ms | 49 self.timeout = timeout # in ms |
| 52 self.image_hash = image_hash | 50 self.image_hash = image_hash |
| 53 self.should_run_pixel_test = should_run_pixel_test | 51 self.should_run_pixel_test = should_run_pixel_test |
| 54 self.args = args | 52 self.args = args |
| 55 | 53 |
| 56 | 54 |
| 57 class DriverOutput(object): | 55 class DriverOutput(object): |
| 58 """Groups information about a output from driver for easy passing | 56 """Groups information about a output from driver for easy passing |
| 59 and post-processing of data.""" | 57 and post-processing of data.""" |
| 60 | 58 |
| 61 def __init__(self, text, image, image_hash, audio, crash=False, | 59 def __init__(self, |
| 62 test_time=0, measurements=None, timeout=False, error='', crashed_pro
cess_name='??', | 60 text, |
| 63 crashed_pid=None, crash_log=None, leak=False, leak_log=None, pid=Non
e): | 61 image, |
| 62 image_hash, |
| 63 audio, |
| 64 crash=False, |
| 65 test_time=0, |
| 66 measurements=None, |
| 67 timeout=False, |
| 68 error='', |
| 69 crashed_process_name='??', |
| 70 crashed_pid=None, |
| 71 crash_log=None, |
| 72 leak=False, |
| 73 leak_log=None, |
| 74 pid=None): |
| 64 # FIXME: Args could be renamed to better clarify what they do. | 75 # FIXME: Args could be renamed to better clarify what they do. |
| 65 self.text = text | 76 self.text = text |
| 66 self.image = image # May be empty-string if the test crashes. | 77 self.image = image # May be empty-string if the test crashes. |
| 67 self.image_hash = image_hash | 78 self.image_hash = image_hash |
| 68 self.image_diff = None # image_diff gets filled in after construction. | 79 self.image_diff = None # image_diff gets filled in after construction. |
| 69 self.audio = audio # Binary format is port-dependent. | 80 self.audio = audio # Binary format is port-dependent. |
| 70 self.crash = crash | 81 self.crash = crash |
| 71 self.crashed_process_name = crashed_process_name | 82 self.crashed_process_name = crashed_process_name |
| 72 self.crashed_pid = crashed_pid | 83 self.crashed_pid = crashed_pid |
| 73 self.crash_log = crash_log | 84 self.crash_log = crash_log |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 125 # FIXME: We should probably remove _read_first_block and _read_optional_
image_block and | 136 # FIXME: We should probably remove _read_first_block and _read_optional_
image_block and |
| 126 # instead scope these locally in run_test. | 137 # instead scope these locally in run_test. |
| 127 self.error_from_test = str() | 138 self.error_from_test = str() |
| 128 self.err_seen_eof = False | 139 self.err_seen_eof = False |
| 129 self._server_process = None | 140 self._server_process = None |
| 130 self._current_cmd_line = None | 141 self._current_cmd_line = None |
| 131 | 142 |
| 132 self._measurements = {} | 143 self._measurements = {} |
| 133 if self._port.get_option("profile"): | 144 if self._port.get_option("profile"): |
| 134 profiler_name = self._port.get_option("profiler") | 145 profiler_name = self._port.get_option("profiler") |
| 135 self._profiler = ProfilerFactory.create_profiler(self._port.host, | 146 self._profiler = ProfilerFactory.create_profiler(self._port.host, se
lf._port._path_to_driver(), |
| 136 self._port._path_to_driver(), self._port.results_directory(), pr
ofiler_name) | 147 self._port.results_
directory(), profiler_name) |
| 137 else: | 148 else: |
| 138 self._profiler = None | 149 self._profiler = None |
| 139 | 150 |
| 140 def __del__(self): | 151 def __del__(self): |
| 141 self.stop() | 152 self.stop() |
| 142 | 153 |
| 143 def run_test(self, driver_input, stop_when_done): | 154 def run_test(self, driver_input, stop_when_done): |
| 144 """Run a single test and return the results. | 155 """Run a single test and return the results. |
| 145 | 156 |
| 146 Note that it is okay if a test times out or crashes. content_shell | 157 Note that it is okay if a test times out or crashes. content_shell |
| (...skipping 18 matching lines...) Expand all Loading... |
| 165 image, actual_image_hash = self._read_optional_image_block(deadline) #
The second (optional) block is image data. | 176 image, actual_image_hash = self._read_optional_image_block(deadline) #
The second (optional) block is image data. |
| 166 | 177 |
| 167 crashed = self.has_crashed() | 178 crashed = self.has_crashed() |
| 168 timed_out = self._server_process.timed_out | 179 timed_out = self._server_process.timed_out |
| 169 pid = self._server_process.pid() | 180 pid = self._server_process.pid() |
| 170 leaked = self._leaked | 181 leaked = self._leaked |
| 171 | 182 |
| 172 if not crashed: | 183 if not crashed: |
| 173 sanitizer = self._port.output_contains_sanitizer_messages(self.error
_from_test) | 184 sanitizer = self._port.output_contains_sanitizer_messages(self.error
_from_test) |
| 174 if sanitizer: | 185 if sanitizer: |
| 175 self.error_from_test = 'OUTPUT CONTAINS "' + sanitizer + '", so
we are treating this test as if it crashed, even though it did not.\n\n' + self.
error_from_test | 186 self.error_from_test = 'OUTPUT CONTAINS "' + sanitizer + \ |
| 187 '", so we are treating this test as if it crashed, even thou
gh it did not.\n\n' + self.error_from_test |
| 176 crashed = True | 188 crashed = True |
| 177 self._crashed_process_name = "unknown process name" | 189 self._crashed_process_name = "unknown process name" |
| 178 self._crashed_pid = 0 | 190 self._crashed_pid = 0 |
| 179 | 191 |
| 180 if stop_when_done or crashed or timed_out or leaked: | 192 if stop_when_done or crashed or timed_out or leaked: |
| 181 # We call stop() even if we crashed or timed out in order to get any
remaining stdout/stderr output. | 193 # We call stop() even if we crashed or timed out in order to get any
remaining stdout/stderr output. |
| 182 # In the timeout case, we kill the hung process as well. | 194 # In the timeout case, we kill the hung process as well. |
| 183 out, err = self._server_process.stop(self._port.driver_stop_timeout(
) if stop_when_done else 0.0) | 195 out, err = self._server_process.stop(self._port.driver_stop_timeout(
) if stop_when_done else 0.0) |
| 184 if out: | 196 if out: |
| 185 text += out | 197 text += out |
| (...skipping 10 matching lines...) Expand all Loading... |
| 196 pid_str = str(self._crashed_pid) if self._crashed_pid else "unkn
own pid" | 208 pid_str = str(self._crashed_pid) if self._crashed_pid else "unkn
own pid" |
| 197 crash_log = 'No crash log found for %s:%s.\n' % (self._crashed_p
rocess_name, pid_str) | 209 crash_log = 'No crash log found for %s:%s.\n' % (self._crashed_p
rocess_name, pid_str) |
| 198 # If we were unresponsive append a message informing there may n
ot have been a crash. | 210 # If we were unresponsive append a message informing there may n
ot have been a crash. |
| 199 if self._subprocess_was_unresponsive: | 211 if self._subprocess_was_unresponsive: |
| 200 crash_log += 'Process failed to become responsive before tim
ing out.\n' | 212 crash_log += 'Process failed to become responsive before tim
ing out.\n' |
| 201 | 213 |
| 202 # Print stdout and stderr to the placeholder crash log; we want
as much context as possible. | 214 # Print stdout and stderr to the placeholder crash log; we want
as much context as possible. |
| 203 if self.error_from_test: | 215 if self.error_from_test: |
| 204 crash_log += '\nstdout:\n%s\nstderr:\n%s\n' % (text, self.er
ror_from_test) | 216 crash_log += '\nstdout:\n%s\nstderr:\n%s\n' % (text, self.er
ror_from_test) |
| 205 | 217 |
| 206 return DriverOutput(text, image, actual_image_hash, audio, | 218 return DriverOutput(text, |
| 207 crash=crashed, test_time=time.time() - test_begin_time, measurements
=self._measurements, | 219 image, |
| 208 timeout=timed_out, error=self.error_from_test, | 220 actual_image_hash, |
| 209 crashed_process_name=self._crashed_process_name, | 221 audio, |
| 210 crashed_pid=self._crashed_pid, crash_log=crash_log, | 222 crash=crashed, |
| 211 leak=leaked, leak_log=self._leak_log, | 223 test_time=time.time() - test_begin_time, |
| 212 pid=pid) | 224 measurements=self._measurements, |
| 225 timeout=timed_out, |
| 226 error=self.error_from_test, |
| 227 crashed_process_name=self._crashed_process_name, |
| 228 crashed_pid=self._crashed_pid, |
| 229 crash_log=crash_log, |
| 230 leak=leaked, |
| 231 leak_log=self._leak_log, |
| 232 pid=pid) |
| 213 | 233 |
| 214 def _get_crash_log(self, stdout, stderr, newer_than): | 234 def _get_crash_log(self, stdout, stderr, newer_than): |
| 215 return self._port._get_crash_log(self._crashed_process_name, self._crash
ed_pid, stdout, stderr, newer_than) | 235 return self._port._get_crash_log(self._crashed_process_name, self._crash
ed_pid, stdout, stderr, newer_than) |
| 216 | 236 |
| 217 # FIXME: Seems this could just be inlined into callers. | 237 # FIXME: Seems this could just be inlined into callers. |
| 218 @classmethod | 238 @classmethod |
| 219 def _command_wrapper(cls, wrapper_option): | 239 def _command_wrapper(cls, wrapper_option): |
| 220 # Hook for injecting valgrind or other runtime instrumentation, | 240 # Hook for injecting valgrind or other runtime instrumentation, |
| 221 # used by e.g. tools/valgrind/valgrind_tests.py. | 241 # used by e.g. tools/valgrind/valgrind_tests.py. |
| 222 return shlex.split(wrapper_option) if wrapper_option else [] | 242 return shlex.split(wrapper_option) if wrapper_option else [] |
| (...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 312 self.stop() | 332 self.stop() |
| 313 self._driver_tempdir = self._port._filesystem.mkdtemp(prefix='%s-' % sel
f._port.driver_name()) | 333 self._driver_tempdir = self._port._filesystem.mkdtemp(prefix='%s-' % sel
f._port.driver_name()) |
| 314 server_name = self._port.driver_name() | 334 server_name = self._port.driver_name() |
| 315 environment = self._port.setup_environ_for_server(server_name) | 335 environment = self._port.setup_environ_for_server(server_name) |
| 316 environment = self._setup_environ_for_driver(environment) | 336 environment = self._setup_environ_for_driver(environment) |
| 317 self._crashed_process_name = None | 337 self._crashed_process_name = None |
| 318 self._crashed_pid = None | 338 self._crashed_pid = None |
| 319 self._leaked = False | 339 self._leaked = False |
| 320 self._leak_log = None | 340 self._leak_log = None |
| 321 cmd_line = self.cmd_line(pixel_tests, per_test_args) | 341 cmd_line = self.cmd_line(pixel_tests, per_test_args) |
| 322 self._server_process = self._port._server_process_constructor(self._port
, server_name, cmd_line, environment, logging=self._port.get_option("driver_logg
ing")) | 342 self._server_process = self._port._server_process_constructor(self._port
, |
| 343 server_nam
e, |
| 344 cmd_line, |
| 345 environmen
t, |
| 346 logging=se
lf._port.get_option("driver_logging")) |
| 323 self._server_process.start() | 347 self._server_process.start() |
| 324 self._current_cmd_line = cmd_line | 348 self._current_cmd_line = cmd_line |
| 325 | 349 |
| 326 if wait_for_ready: | 350 if wait_for_ready: |
| 327 deadline = time.time() + DRIVER_START_TIMEOUT_SECS | 351 deadline = time.time() + DRIVER_START_TIMEOUT_SECS |
| 328 if not self._wait_for_server_process_output(self._server_process, de
adline, '#READY'): | 352 if not self._wait_for_server_process_output(self._server_process, de
adline, '#READY'): |
| 329 _log.error("content_shell took too long to startup.") | 353 _log.error("content_shell took too long to startup.") |
| 330 | 354 |
| 331 def _wait_for_server_process_output(self, server_process, deadline, text): | 355 def _wait_for_server_process_output(self, server_process, deadline, text): |
| 332 output = '' | 356 output = '' |
| (...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 375 cmd.extend(per_test_args) | 399 cmd.extend(per_test_args) |
| 376 cmd.append('-') | 400 cmd.append('-') |
| 377 return cmd | 401 return cmd |
| 378 | 402 |
| 379 def _check_for_driver_crash(self, error_line): | 403 def _check_for_driver_crash(self, error_line): |
| 380 if error_line == "#CRASHED\n": | 404 if error_line == "#CRASHED\n": |
| 381 # This is used on Windows to report that the process has crashed | 405 # This is used on Windows to report that the process has crashed |
| 382 # See http://trac.webkit.org/changeset/65537. | 406 # See http://trac.webkit.org/changeset/65537. |
| 383 self._crashed_process_name = self._server_process.name() | 407 self._crashed_process_name = self._server_process.name() |
| 384 self._crashed_pid = self._server_process.pid() | 408 self._crashed_pid = self._server_process.pid() |
| 385 elif (error_line.startswith("#CRASHED - ") | 409 elif (error_line.startswith("#CRASHED - ") or error_line.startswith("#PR
OCESS UNRESPONSIVE - ")): |
| 386 or error_line.startswith("#PROCESS UNRESPONSIVE - ")): | |
| 387 # WebKitTestRunner uses this to report that the WebProcess subproces
s crashed. | 410 # WebKitTestRunner uses this to report that the WebProcess subproces
s crashed. |
| 388 match = re.match('#(?:CRASHED|PROCESS UNRESPONSIVE) - (\S+)', error_
line) | 411 match = re.match('#(?:CRASHED|PROCESS UNRESPONSIVE) - (\S+)', error_
line) |
| 389 self._crashed_process_name = match.group(1) if match else 'WebProces
s' | 412 self._crashed_process_name = match.group(1) if match else 'WebProces
s' |
| 390 match = re.search('pid (\d+)', error_line) | 413 match = re.search('pid (\d+)', error_line) |
| 391 pid = int(match.group(1)) if match else None | 414 pid = int(match.group(1)) if match else None |
| 392 self._crashed_pid = pid | 415 self._crashed_pid = pid |
| 393 # FIXME: delete this after we're sure this code is working :) | 416 # FIXME: delete this after we're sure this code is working :) |
| 394 _log.debug('%s crash, pid = %s, error_line = %s' % (self._crashed_pr
ocess_name, str(pid), error_line)) | 417 _log.debug('%s crash, pid = %s, error_line = %s' % (self._crashed_pr
ocess_name, str(pid), error_line)) |
| 395 if error_line.startswith("#PROCESS UNRESPONSIVE - "): | 418 if error_line.startswith("#PROCESS UNRESPONSIVE - "): |
| 396 self._subprocess_was_unresponsive = True | 419 self._subprocess_was_unresponsive = True |
| 397 self._port.sample_process(self._crashed_process_name, self._cras
hed_pid) | 420 self._port.sample_process(self._crashed_process_name, self._cras
hed_pid) |
| 398 # We want to show this since it's not a regular crash and probab
ly we don't have a crash log. | 421 # We want to show this since it's not a regular crash and probab
ly we don't have a crash log. |
| 399 self.error_from_test += error_line | 422 self.error_from_test += error_line |
| 400 return True | 423 return True |
| 401 return self.has_crashed() | 424 return self.has_crashed() |
| 402 | 425 |
| 403 def _check_for_leak(self, error_line): | 426 def _check_for_leak(self, error_line): |
| 404 if error_line.startswith("#LEAK - "): | 427 if error_line.startswith("#LEAK - "): |
| 405 self._leaked = True | 428 self._leaked = True |
| 406 match = re.match('#LEAK - (\S+) pid (\d+) (.+)\n', error_line) | 429 match = re.match('#LEAK - (\S+) pid (\d+) (.+)\n', error_line) |
| 407 self._leak_log = match.group(3) | 430 self._leak_log = match.group(3) |
| 408 return self._leaked | 431 return self._leaked |
| 409 | 432 |
| 410 def _command_from_driver_input(self, driver_input): | 433 def _command_from_driver_input(self, driver_input): |
| 411 # FIXME: performance tests pass in full URLs instead of test names. | 434 # FIXME: performance tests pass in full URLs instead of test names. |
| 412 if driver_input.test_name.startswith('http://') or driver_input.test_nam
e.startswith('https://') or driver_input.test_name == ('about:blank'): | 435 if driver_input.test_name.startswith('http://') or driver_input.test_nam
e.startswith( |
| 436 'https://') or driver_input.test_name == ('about:blank'): |
| 413 command = driver_input.test_name | 437 command = driver_input.test_name |
| 414 elif self.is_http_test(driver_input.test_name) or self._should_treat_as_
wpt_test(driver_input.test_name): | 438 elif self.is_http_test(driver_input.test_name) or self._should_treat_as_
wpt_test(driver_input.test_name): |
| 415 command = self.test_to_uri(driver_input.test_name) | 439 command = self.test_to_uri(driver_input.test_name) |
| 416 else: | 440 else: |
| 417 command = self._port.abspath_for_test(driver_input.test_name) | 441 command = self._port.abspath_for_test(driver_input.test_name) |
| 418 if sys.platform == 'cygwin': | 442 if sys.platform == 'cygwin': |
| 419 command = path.cygpath(command) | 443 command = path.cygpath(command) |
| 420 | 444 |
| 421 assert not driver_input.image_hash or driver_input.should_run_pixel_test | 445 assert not driver_input.image_hash or driver_input.should_run_pixel_test |
| 422 | 446 |
| (...skipping 27 matching lines...) Expand all Loading... |
| 450 def _read_header(self, block, line, header_text, header_attr, header_filter=
None): | 474 def _read_header(self, block, line, header_text, header_attr, header_filter=
None): |
| 451 if line.startswith(header_text) and getattr(block, header_attr) is None: | 475 if line.startswith(header_text) and getattr(block, header_attr) is None: |
| 452 value = line.split()[1] | 476 value = line.split()[1] |
| 453 if header_filter: | 477 if header_filter: |
| 454 value = header_filter(value) | 478 value = header_filter(value) |
| 455 setattr(block, header_attr, value) | 479 setattr(block, header_attr, value) |
| 456 return True | 480 return True |
| 457 return False | 481 return False |
| 458 | 482 |
| 459 def _process_stdout_line(self, block, line): | 483 def _process_stdout_line(self, block, line): |
| 460 if (self._read_header(block, line, 'Content-Type: ', 'content_type') | 484 if (self._read_header(block, line, 'Content-Type: ', 'content_type') or |
| 461 or self._read_header(block, line, 'Content-Transfer-Encoding: ', 'en
coding') | 485 self._read_header(block, line, 'Content-Transfer-Encoding: ', 'e
ncoding') or |
| 462 or self._read_header(block, line, 'Content-Length: ', '_content_leng
th', int) | 486 self._read_header(block, line, 'Content-Length: ', '_content_len
gth', int) or |
| 463 or self._read_header(block, line, 'ActualHash: ', 'content_hash') | 487 self._read_header(block, line, 'ActualHash: ', 'content_hash') o
r |
| 464 or self._read_header(block, line, 'DumpMalloc: ', 'malloc') | 488 self._read_header(block, line, 'DumpMalloc: ', 'malloc') or |
| 465 or self._read_header(block, line, 'DumpJSHeap: ', 'js_heap') | 489 self._read_header(block, line, 'DumpJSHeap: ', 'js_heap') or |
| 466 or self._read_header(block, line, 'StdinPath', 'stdin_path')): | 490 self._read_header(block, line, 'StdinPath', 'stdin_path')): |
| 467 return | 491 return |
| 468 # Note, we're not reading ExpectedHash: here, but we could. | 492 # Note, we're not reading ExpectedHash: here, but we could. |
| 469 # If the line wasn't a header, we just append it to the content. | 493 # If the line wasn't a header, we just append it to the content. |
| 470 block.content += line | 494 block.content += line |
| 471 | 495 |
| 472 def _strip_eof(self, line): | 496 def _strip_eof(self, line): |
| 473 if line and line.endswith("#EOF\n"): | 497 if line and line.endswith("#EOF\n"): |
| 474 return line[:-5], True | 498 return line[:-5], True |
| 475 if line and line.endswith("#EOF\r\n"): | 499 if line and line.endswith("#EOF\r\n"): |
| 476 _log.error("Got a CRLF-terminated #EOF - this is a driver bug.") | 500 _log.error("Got a CRLF-terminated #EOF - this is a driver bug.") |
| (...skipping 22 matching lines...) Expand all Loading... |
| 499 | 523 |
| 500 if out_line: | 524 if out_line: |
| 501 assert not out_seen_eof | 525 assert not out_seen_eof |
| 502 out_line, out_seen_eof = self._strip_eof(out_line) | 526 out_line, out_seen_eof = self._strip_eof(out_line) |
| 503 if err_line: | 527 if err_line: |
| 504 assert not self.err_seen_eof | 528 assert not self.err_seen_eof |
| 505 err_line, self.err_seen_eof = self._strip_eof(err_line) | 529 err_line, self.err_seen_eof = self._strip_eof(err_line) |
| 506 | 530 |
| 507 if out_line: | 531 if out_line: |
| 508 if out_line[-1] != "\n": | 532 if out_line[-1] != "\n": |
| 509 _log.error("Last character read from DRT stdout line was not
a newline! This indicates either a NRWT or DRT bug.") | 533 _log.error( |
| 534 "Last character read from DRT stdout line was not a newl
ine! This indicates either a NRWT or DRT bug.") |
| 510 content_length_before_header_check = block._content_length | 535 content_length_before_header_check = block._content_length |
| 511 self._process_stdout_line(block, out_line) | 536 self._process_stdout_line(block, out_line) |
| 512 # FIXME: Unlike HTTP, DRT dumps the content right after printing
a Content-Length header. | 537 # FIXME: Unlike HTTP, DRT dumps the content right after printing
a Content-Length header. |
| 513 # Don't wait until we're done with headers, just read the binary
blob right now. | 538 # Don't wait until we're done with headers, just read the binary
blob right now. |
| 514 if content_length_before_header_check != block._content_length: | 539 if content_length_before_header_check != block._content_length: |
| 515 if block._content_length > 0: | 540 if block._content_length > 0: |
| 516 block.content = self._server_process.read_stdout(deadlin
e, block._content_length) | 541 block.content = self._server_process.read_stdout(deadlin
e, block._content_length) |
| 517 else: | 542 else: |
| 518 _log.error("Received content of type %s with Content-Len
gth of 0! This indicates a bug in %s.", | 543 _log.error("Received content of type %s with Content-Len
gth of 0! This indicates a bug in %s.", |
| 519 block.content_type, self._server_process.name
()) | 544 block.content_type, self._server_process.name
()) |
| (...skipping 20 matching lines...) Expand all Loading... |
| 540 self.decoded_content = None | 565 self.decoded_content = None |
| 541 self.malloc = None | 566 self.malloc = None |
| 542 self.js_heap = None | 567 self.js_heap = None |
| 543 self.stdin_path = None | 568 self.stdin_path = None |
| 544 | 569 |
| 545 def decode_content(self): | 570 def decode_content(self): |
| 546 if self.encoding == 'base64' and self.content is not None: | 571 if self.encoding == 'base64' and self.content is not None: |
| 547 self.decoded_content = base64.b64decode(self.content) | 572 self.decoded_content = base64.b64decode(self.content) |
| 548 else: | 573 else: |
| 549 self.decoded_content = self.content | 574 self.decoded_content = self.content |
| OLD | NEW |