Fix logging issues in the debugger. (#2483)

- Properly handle logging during transport close
 - Properly display data during parse

Furthermore hide global functions of the debugger.

JerryScript-DCO-1.0-Signed-off-by: Zoltan Herczeg zherczeg.u-szeged@partner.samsung.com
This commit is contained in:
Zoltan Herczeg 2018-09-03 11:14:57 +02:00 committed by GitHub
parent d270f82ecb
commit 2ad883ea48
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 285 additions and 84 deletions

View File

@ -146,6 +146,8 @@ jerry_debugger_transport_close (void)
return;
}
JERRY_CONTEXT (debugger_flags) = JERRY_DEBUGGER_VM_IGNORE;
jerry_debugger_transport_header_t *current_p = JERRY_CONTEXT (debugger_transport_header_p);
JERRY_ASSERT (current_p != NULL);
@ -160,8 +162,6 @@ jerry_debugger_transport_close (void)
}
while (current_p != NULL);
JERRY_CONTEXT (debugger_flags) = JERRY_DEBUGGER_VM_IGNORE;
jerry_port_log (JERRY_LOG_LEVEL_DEBUG, "Debugger client connection closed.\n");
jerry_debugger_free_unreferenced_byte_code ();

View File

@ -280,6 +280,8 @@ class JerryDebugger(object):
self.client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.client_socket.connect((self.host, self.port))
self.non_interactive = False
self.current_out = b""
self.current_log = b""
self.send_message(b"GET /jerry-debugger HTTP/1.1\r\n" +
b"Upgrade: websocket\r\n" +
@ -824,48 +826,8 @@ class JerryDebugger(object):
JERRY_DEBUGGER_EVAL_RESULT_END,
JERRY_DEBUGGER_OUTPUT_RESULT,
JERRY_DEBUGGER_OUTPUT_RESULT_END]:
message = b""
msg_type = buffer_type
while True:
if buffer_type in [JERRY_DEBUGGER_EVAL_RESULT_END,
JERRY_DEBUGGER_OUTPUT_RESULT_END]:
subtype = ord(data[-1])
message += data[3:-1]
break
else:
message += data[3:]
data = self.get_message(True)
buffer_type = ord(data[2])
buffer_size = ord(data[1]) - 1
# Checks if the next frame would be an invalid data frame.
# If it is not the message type, or the end type of it, an exception is thrown.
if buffer_type not in [msg_type, msg_type + 1]:
raise Exception("Invalid data caught")
if not message.endswith("\n"):
message += "\n"
# Subtypes of output
if buffer_type == JERRY_DEBUGGER_OUTPUT_RESULT_END:
if subtype in [JERRY_DEBUGGER_OUTPUT_OK,
JERRY_DEBUGGER_OUTPUT_DEBUG]:
result += "%sout: %s%s" % (self.blue, self.nocolor, message)
elif subtype == JERRY_DEBUGGER_OUTPUT_WARNING:
result += "%swarning: %s%s" % (self.yellow, self.nocolor, message)
elif subtype == JERRY_DEBUGGER_OUTPUT_ERROR:
result += "%serr: %s%s" % (self.red, self.nocolor, message)
elif subtype == JERRY_DEBUGGER_OUTPUT_TRACE:
result += "%strace: %s%s" % (self.blue, self.nocolor, message)
# Subtypes of eval
else:
self.prompt = True
if subtype == JERRY_DEBUGGER_EVAL_ERROR:
result += "Uncaught exception: %s" % (message)
else:
result += message
result = self._process_incoming_text(buffer_type, data)
return DebuggerAction(DebuggerAction.TEXT, result)
elif buffer_type == JERRY_DEBUGGER_MEMSTATS_RECEIVE:
@ -936,6 +898,7 @@ class JerryDebugger(object):
"lines": [],
"offsets": []}]
new_function_list = {}
result = ""
while True:
if data is None:
@ -1029,6 +992,10 @@ class JerryDebugger(object):
else:
self._release_function(data)
elif buffer_type in [JERRY_DEBUGGER_OUTPUT_RESULT,
JERRY_DEBUGGER_OUTPUT_RESULT_END]:
result += self._process_incoming_text(buffer_type, data)
else:
logging.error("Parser error!")
raise Exception("Unexpected message")
@ -1044,8 +1011,7 @@ class JerryDebugger(object):
# Try to set the pending breakpoints
if self.pending_breakpoint_list:
result = ""
logging.debug("Pending breakpoints list: %s", self.pending_breakpoint_list)
logging.debug("Pending breakpoints available")
bp_list = self.pending_breakpoint_list
for breakpoint_index, breakpoint in bp_list.items():
@ -1076,7 +1042,7 @@ class JerryDebugger(object):
return result
logging.debug("No pending breakpoints")
return ""
return result
def _release_function(self, data):
@ -1176,3 +1142,62 @@ class JerryDebugger(object):
nearest_offset = current_offset
return (function.offsets[nearest_offset], False)
def _process_incoming_text(self, buffer_type, data):
message = b""
msg_type = buffer_type
while True:
if buffer_type in [JERRY_DEBUGGER_EVAL_RESULT_END,
JERRY_DEBUGGER_OUTPUT_RESULT_END]:
subtype = ord(data[-1])
message += data[3:-1]
break
else:
message += data[3:]
data = self.get_message(True)
buffer_type = ord(data[2])
# Checks if the next frame would be an invalid data frame.
# If it is not the message type, or the end type of it, an exception is thrown.
if buffer_type not in [msg_type, msg_type + 1]:
raise Exception("Invalid data caught")
# Subtypes of output
if buffer_type == JERRY_DEBUGGER_OUTPUT_RESULT_END:
if subtype == JERRY_DEBUGGER_OUTPUT_OK:
log_type = "%sout:%s " % (self.blue, self.nocolor)
message = self.current_out + message
lines = message.split("\n")
self.current_out = lines.pop()
return "".join(["%s%s\n" % (log_type, line) for line in lines])
if subtype == JERRY_DEBUGGER_OUTPUT_DEBUG:
log_type = "%slog:%s " % (self.yellow, self.nocolor)
message = self.current_log + message
lines = message.split("\n")
self.current_log = lines.pop()
return "".join(["%s%s\n" % (log_type, line) for line in lines])
if not message.endswith("\n"):
message += "\n"
if subtype == JERRY_DEBUGGER_OUTPUT_WARNING:
return "%swarning: %s%s" % (self.yellow, self.nocolor, message)
elif subtype == JERRY_DEBUGGER_OUTPUT_ERROR:
return "%serr: %s%s" % (self.red, self.nocolor, message)
elif subtype == JERRY_DEBUGGER_OUTPUT_TRACE:
return "%strace: %s%s" % (self.blue, self.nocolor, message)
# Subtypes of eval
self.prompt = True
if not message.endswith("\n"):
message += "\n"
if subtype == JERRY_DEBUGGER_EVAL_ERROR:
return "Uncaught exception: %s" % (message)
return message

View File

@ -48,7 +48,7 @@ jerryx_debugger_tcp_log_error (int err_val)
static void
jerryx_debugger_tcp_close (jerry_debugger_transport_header_t *header_p) /**< tcp implementation */
{
JERRYX_ASSERT (jerry_debugger_transport_is_connected ());
JERRYX_ASSERT (!jerry_debugger_transport_is_connected ());
jerryx_debugger_transport_tcp_t *tcp_p = (jerryx_debugger_transport_tcp_t *) header_p;

View File

@ -275,7 +275,7 @@ jerryx_process_handshake (uint8_t *request_buffer_p) /**< temporary buffer */
static void
jerryx_debugger_ws_close (jerry_debugger_transport_header_t *header_p) /**< tcp implementation */
{
JERRYX_ASSERT (jerry_debugger_transport_is_connected ());
JERRYX_ASSERT (!jerry_debugger_transport_is_connected ());
jerry_debugger_transport_free ((void *) header_p, sizeof (jerry_debugger_transport_header_t));
} /* jerryx_debugger_ws_close */

View File

@ -48,60 +48,95 @@ jerryx_handler_print (const jerry_value_t func_obj_val, /**< function object */
jerry_value_t ret_val = jerry_create_undefined ();
for (jerry_length_t arg_index = 0;
jerry_value_is_undefined (ret_val) && arg_index < args_cnt;
arg_index++)
for (jerry_length_t arg_index = 0; arg_index < args_cnt; arg_index++)
{
jerry_value_t str_val = jerry_value_to_string (args_p[arg_index]);
if (!jerry_value_is_error (str_val))
if (jerry_value_is_error (str_val))
{
if (arg_index != 0)
/* There is no need to free the undefined value. */
ret_val = str_val;
break;
}
jerry_length_t length = jerry_get_utf8_string_length (str_val);
jerry_length_t substr_pos = 0;
jerry_char_t substr_buf[256];
do
{
jerry_size_t substr_size = jerry_substring_to_utf8_char_buffer (str_val,
substr_pos,
length,
substr_buf,
256 - 1);
jerry_char_t *buf_end_p = substr_buf + substr_size;
/* Update start position by the number of utf-8 characters. */
for (jerry_char_t *buf_p = substr_buf; buf_p < buf_end_p; buf_p++)
{
jerryx_port_handler_print_char (' ');
/* Skip intermediate utf-8 octets. */
if ((*buf_p & 0xc0) != 0x80)
{
substr_pos++;
}
}
jerry_size_t substr_size;
jerry_length_t substr_pos = 0;
jerry_char_t substr_buf[256];
while ((substr_size = jerry_substring_to_utf8_char_buffer (str_val,
substr_pos,
substr_pos + 256,
substr_buf,
256)) != 0)
if (substr_pos == length)
{
*buf_end_p++ = (arg_index < args_cnt - 1) ? ' ' : '\n';
}
#ifdef JERRY_DEBUGGER
jerry_debugger_send_output (substr_buf, substr_size);
jerry_char_t *debugger_start_p = substr_buf;
#endif /* JERRY_DEBUGGER */
for (jerry_size_t chr_index = 0; chr_index < substr_size; chr_index++)
for (jerry_char_t *buf_p = substr_buf; buf_p < buf_end_p; buf_p++)
{
char chr = (char) *buf_p;
if (chr != '\0')
{
char chr = (char) substr_buf[chr_index];
if (chr == '\0')
{
for (jerry_size_t null_index = 0; null_str[null_index] != 0; null_index++)
{
jerryx_port_handler_print_char (null_str[null_index]);
}
}
else
{
jerryx_port_handler_print_char (chr);
}
jerryx_port_handler_print_char (chr);
continue;
}
substr_pos += substr_size;
for (jerry_size_t null_index = 0; null_str[null_index] != '\0'; null_index++)
{
jerryx_port_handler_print_char (null_str[null_index]);
}
#ifdef JERRY_DEBUGGER
if (debugger_start_p < buf_p)
{
jerry_debugger_send_output (debugger_start_p, (jerry_size_t) (buf_p - debugger_start_p));
}
jerry_debugger_send_output ((jerry_char_t *) null_str, 6);
debugger_start_p = buf_p + 1;
#endif /* JERRY_DEBUGGER */
}
jerry_release_value (str_val);
}
else
{
ret_val = str_val;
#ifdef JERRY_DEBUGGER
if (debugger_start_p < buf_end_p)
{
jerry_debugger_send_output (debugger_start_p, (jerry_size_t) (buf_end_p - debugger_start_p));
}
#endif /* JERRY_DEBUGGER */
}
while (substr_pos < length);
jerry_release_value (str_val);
}
jerryx_port_handler_print_char ('\n');
if (args_cnt == 0 || jerry_value_is_error (ret_val))
{
jerryx_port_handler_print_char ('\n');
#ifdef JERRY_DEBUGGER
jerry_debugger_send_output ((jerry_char_t *) "\n", 1);
#endif /* JERRY_DEBUGGER */
}
return ret_val;
} /* jerryx_handler_print */

View File

@ -0,0 +1 @@
c

View File

@ -0,0 +1,112 @@
Connecting to: localhost:5001
Stopped at tests/debugger/do_print.js:15
(jerry-debugger) c
out: Hello world!
out: A [ ] 110 null true undefined
out:
out: [A
out: B C
out: D E
out: F
out: G]
out: 1: Az élet gyönyörű.
out: 2: Az élet gyönyörű.
out: 3: Az élet gyönyörű.
out: 4: Az élet gyönyörű.
out: 5: Az élet gyönyörű.
out: 6: Az élet gyönyörű.
out: 7: Az élet gyönyörű.
out: 8: Az élet gyönyörű.
out: 9: Az élet gyönyörű.
out: 10: Az élet gyönyörű.
out: 11: Az élet gyönyörű.
out: 12: Az élet gyönyörű.
out: 13: Az élet gyönyörű.
out: 14: Az élet gyönyörű.
out: 15: Az élet gyönyörű.
out: 16: Az élet gyönyörű.
out: 17: Az élet gyönyörű.
out: 18: Az élet gyönyörű.
out: 19: Az élet gyönyörű.
out: 20: Az élet gyönyörű.
out: 21: Az élet gyönyörű.
out: 22: Az élet gyönyörű.
out: 23: Az élet gyönyörű.
out: 24: Az élet gyönyörű.
out: 25: Az élet gyönyörű.
out: 26: Az élet gyönyörű.
out: 27: Az élet gyönyörű.
out: 28: Az élet gyönyörű.
out: 29: Az élet gyönyörű.
out: 30: Az élet gyönyörű.
out: 31: Az élet gyönyörű.
out: 32: Az élet gyönyörű.
out: 33: Az élet gyönyörű.
out: 34: Az élet gyönyörű.
out: 35: Az élet gyönyörű.
out: 36: Az élet gyönyörű.
out: 37: Az élet gyönyörű.
out: 38: Az élet gyönyörű.
out: 39: Az élet gyönyörű.
out: 40: Az élet gyönyörű.
out: 41: Az élet gyönyörű.
out: 42: Az élet gyönyörű.
out: 43: Az élet gyönyörű.
out: 44: Az élet gyönyörű.
out: 45: Az élet gyönyörű.
out: 46: Az élet gyönyörű.
out: 47: Az élet gyönyörű.
out: 48: Az élet gyönyörű.
out: 49: Az élet gyönyörű.
out: 50: Az élet gyönyörű.
out: 51: Az élet gyönyörű.
out: 52: Az élet gyönyörű.
out: 53: Az élet gyönyörű.
out: 54: Az élet gyönyörű.
out: 55: Az élet gyönyörű.
out: 56: Az élet gyönyörű.
out: 57: Az élet gyönyörű.
out: 58: Az élet gyönyörű.
out: 59: Az élet gyönyörű.
out: 60: Az élet gyönyörű.
out: 61: Az élet gyönyörű.
out: 62: Az élet gyönyörű.
out: 63: Az élet gyönyörű.
out: 64: Az élet gyönyörű.
out: 65: Az élet gyönyörű.
out: 66: Az élet gyönyörű.
out: 67: Az élet gyönyörű.
out: 68: Az élet gyönyörű.
out: 69: Az élet gyönyörű.
out: 70: Az élet gyönyörű.
out: 71: Az élet gyönyörű.
out: 72: Az élet gyönyörű.
out: 73: Az élet gyönyörű.
out: 74: Az élet gyönyörű.
out: 75: Az élet gyönyörű.
out: 76: Az élet gyönyörű.
out: 77: Az élet gyönyörű.
out: 78: Az élet gyönyörű.
out: 79: Az élet gyönyörű.
out: 80: Az élet gyönyörű.
out: 81: Az élet gyönyörű.
out: 82: Az élet gyönyörű.
out: 83: Az élet gyönyörű.
out: 84: Az élet gyönyörű.
out: 85: Az élet gyönyörű.
out: 86: Az élet gyönyörű.
out: 87: Az élet gyönyörű.
out: 88: Az élet gyönyörű.
out: 89: Az élet gyönyörű.
out: 90: Az élet gyönyörű.
out: 91: Az élet gyönyörű.
out: 92: Az élet gyönyörű.
out: 93: Az élet gyönyörű.
out: 94: Az élet gyönyörű.
out: 95: Az élet gyönyörű.
out: 96: Az élet gyönyörű.
out: 97: Az élet gyönyörű.
out: 98: Az élet gyönyörű.
out: 99: Az élet gyönyörű.
out: 100: Az élet gyönyörű.
out:

View File

@ -0,0 +1,28 @@
// Copyright JS Foundation and other contributors, http://js.foundation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
print("Hello world!");
print("A", "[", "", "]", 1.1e2, null, true, undefined);
print();
print("[A\nB", "C\nD", "E\nF\nG]");
var s = "";
for (i = 1; i <= 100; i++) {
/* Translated from hungarian: life is beautiful */
s += i + ": Az élet gyönyörű.\n";
}
/* Long string with non-ascii characters. */
print(s);