[DevTools] Roll inspector_protocol (V8).

New Revision: d48ba2079ffcdaf2d99f4153127aab6dbe32a954

Change-Id: Idde7388b4f92492609c1714fc003ec3234c8bf82
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1686451
Auto-Submit: Johannes Henkel <johannes@chromium.org>
Reviewed-by: Alexei Filippov <alph@chromium.org>
Commit-Queue: Alexei Filippov <alph@chromium.org>
Cr-Commit-Position: refs/heads/master@{#62503}
This commit is contained in:
Johannes Henkel 2019-07-03 02:40:36 -07:00 committed by Commit Bot
parent 39eab44d22
commit e350e84a00
7 changed files with 794 additions and 724 deletions

View File

@ -15,8 +15,8 @@ https://cs.chromium.org/chromium/src/v8/third_party/inspector_protocol/
See also [Contributing to Chrome Devtools Protocol](https://docs.google.com/document/d/1c-COD2kaK__5iMM5SEx-PzNA7HFmgttcYfOHHX0HaOM/edit).
We're working on enabling standalone builds for parts of this package for
testing and development, please feel free to ignore this for now.
But, if you're familiar with
testing and development.
If you're familiar with
[Chromium's development process](https://www.chromium.org/developers/contributing-code)
and have the depot_tools installed, you may use these commands
to fetch the package (and dependencies) and build and run the tests:
@ -24,8 +24,9 @@ to fetch the package (and dependencies) and build and run the tests:
fetch inspector_protocol
cd src
gn gen out/Release
ninja -C out/Release json_parser_test
out/Release/json_parser_test
ninja -C out/Release encoding_test bindings_test
out/Release/encoding_test
out/Release/bindings_test
You'll probably also need to install g++, since Clang uses this to find the
standard C++ headers. E.g.,

View File

@ -2,7 +2,7 @@ Name: inspector protocol
Short Name: inspector_protocol
URL: https://chromium.googlesource.com/deps/inspector_protocol/
Version: 0
Revision: aec57d43b6a2c41c37fb0a2507108e89a9342177
Revision: 373efb7fe33a7ae84038868ed08b9f1bd328b55d
License: BSD
License File: LICENSE
Security Critical: no

File diff suppressed because it is too large Load Diff

View File

@ -7,33 +7,36 @@ import os.path
import sys
try:
import json
import json
except ImportError:
import simplejson as json
import simplejson as json
import pdl
def main(argv):
if len(argv) < 1:
sys.stderr.write("Usage: %s <protocol-1> [<protocol-2> [, <protocol-3>...]] <output-file>\n" % sys.argv[0])
return 1
if len(argv) < 1:
sys.stderr.write(
"Usage: %s <protocol-1> [<protocol-2> [, <protocol-3>...]] "
"<output-file>\n" % sys.argv[0])
return 1
domains = []
version = None
for protocol in argv[:-1]:
file_name = os.path.normpath(protocol)
if not os.path.isfile(file_name):
sys.stderr.write("Cannot find %s\n" % file_name)
return 1
input_file = open(file_name, "r")
parsed_json = pdl.loads(input_file.read(), file_name)
domains += parsed_json["domains"]
version = parsed_json["version"]
domains = []
version = None
for protocol in argv[:-1]:
file_name = os.path.normpath(protocol)
if not os.path.isfile(file_name):
sys.stderr.write("Cannot find %s\n" % file_name)
return 1
input_file = open(file_name, "r")
parsed_json = pdl.loads(input_file.read(), file_name)
domains += parsed_json["domains"]
version = parsed_json["version"]
output_file = open(argv[-1], "w")
json.dump({"version": version, "domains": domains}, output_file, indent=4, sort_keys=False, separators=(',', ': '))
output_file.close()
output_file = open(argv[-1], "w")
json.dump({"version": version, "domains": domains}, output_file,
indent=4, sort_keys=False, separators=(',', ': '))
output_file.close()
if __name__ == '__main__':
sys.exit(main(sys.argv[1:]))
sys.exit(main(sys.argv[1:]))

View File

@ -1370,7 +1370,7 @@ class JSONEncoder : public StreamingParserHandler {
// If we have enough bytes in our input, decode the remaining ones
// belonging to this Unicode character into |codepoint|.
if (ii + num_bytes_left > chars.size())
if (ii + num_bytes_left >= chars.size())
continue;
while (num_bytes_left > 0) {
c = chars[++ii];

View File

@ -1366,6 +1366,32 @@ TEST(JsonEncoder, OverlongEncodings) {
EXPECT_EQ("\"\"", out); // Empty string means that 0x7f was rejected (good).
}
TEST(JsonEncoder, IncompleteUtf8Sequence) {
std::string out;
Status status;
std::unique_ptr<StreamingParserHandler> writer =
NewJSONEncoder(&GetTestPlatform(), &out, &status);
writer->HandleArrayBegin(); // This emits [, which starts an array.
{ // 🌎 takes four bytes to encode in UTF-8. We test with the first three;
// This means we're trying to emit a string that consists solely of an
// incomplete UTF-8 sequence. So the string in the JSON output is emtpy.
std::string world_utf8 = "🌎";
ASSERT_EQ(4u, world_utf8.size());
std::vector<uint8_t> chars(world_utf8.begin(), world_utf8.begin() + 3);
writer->HandleString8(SpanFrom(chars));
EXPECT_EQ("[\"\"", out); // Incomplete sequence rejected: empty string.
}
{ // This time, the incomplete sequence is at the end of the string.
std::string msg = "Hello, \xF0\x9F\x8C";
std::vector<uint8_t> chars(msg.begin(), msg.end());
writer->HandleString8(SpanFrom(chars));
EXPECT_EQ("[\"\",\"Hello, \"", out); // Incomplete sequence dropped at end.
}
}
TEST(JsonStdStringWriterTest, HelloWorld) {
std::string out;
Status status;

View File

@ -12,160 +12,167 @@ import sys
description = ''
primitiveTypes = ['integer', 'number', 'boolean', 'string', 'object', 'any', 'array', 'binary']
primitiveTypes = ['integer', 'number', 'boolean', 'string', 'object',
'any', 'array', 'binary']
def assignType(item, type, is_array=False, map_binary_to_string=False):
if is_array:
item['type'] = 'array'
item['items'] = collections.OrderedDict()
assignType(item['items'], type, False, map_binary_to_string)
return
if is_array:
item['type'] = 'array'
item['items'] = collections.OrderedDict()
assignType(item['items'], type, False, map_binary_to_string)
return
if type == 'enum':
type = 'string'
if map_binary_to_string and type == 'binary':
type = 'string'
if type in primitiveTypes:
item['type'] = type
else:
item['$ref'] = type
if type == 'enum':
type = 'string'
if map_binary_to_string and type == 'binary':
type = 'string'
if type in primitiveTypes:
item['type'] = type
else:
item['$ref'] = type
def createItem(d, experimental, deprecated, name=None):
result = collections.OrderedDict(d)
if name:
result['name'] = name
global description
if description:
result['description'] = description.strip()
if experimental:
result['experimental'] = True
if deprecated:
result['deprecated'] = True
return result
result = collections.OrderedDict(d)
if name:
result['name'] = name
global description
if description:
result['description'] = description.strip()
if experimental:
result['experimental'] = True
if deprecated:
result['deprecated'] = True
return result
def parse(data, file_name, map_binary_to_string=False):
protocol = collections.OrderedDict()
protocol['version'] = collections.OrderedDict()
protocol['domains'] = []
domain = None
item = None
subitems = None
nukeDescription = False
global description
lines = data.split('\n')
for i in range(0, len(lines)):
if nukeDescription:
description = ''
nukeDescription = False
line = lines[i]
trimLine = line.strip()
protocol = collections.OrderedDict()
protocol['version'] = collections.OrderedDict()
protocol['domains'] = []
domain = None
item = None
subitems = None
nukeDescription = False
global description
lines = data.split('\n')
for i in range(0, len(lines)):
if nukeDescription:
description = ''
nukeDescription = False
line = lines[i]
trimLine = line.strip()
if trimLine.startswith('#'):
if len(description):
description += '\n'
description += trimLine[2:]
continue
if trimLine.startswith('#'):
if len(description):
description += '\n'
description += trimLine[2:]
continue
else:
nukeDescription = True
if len(trimLine) == 0:
continue
match = re.compile(
r'^(experimental )?(deprecated )?domain (.*)').match(line)
if match:
domain = createItem({'domain' : match.group(3)}, match.group(1),
match.group(2))
protocol['domains'].append(domain)
continue
match = re.compile(r'^ depends on ([^\s]+)').match(line)
if match:
if 'dependencies' not in domain:
domain['dependencies'] = []
domain['dependencies'].append(match.group(1))
continue
match = re.compile(r'^ (experimental )?(deprecated )?type (.*) '
r'extends (array of )?([^\s]+)').match(line)
if match:
if 'types' not in domain:
domain['types'] = []
item = createItem({'id': match.group(3)}, match.group(1), match.group(2))
assignType(item, match.group(5), match.group(4), map_binary_to_string)
domain['types'].append(item)
continue
match = re.compile(
r'^ (experimental )?(deprecated )?(command|event) (.*)').match(line)
if match:
list = []
if match.group(3) == 'command':
if 'commands' in domain:
list = domain['commands']
else:
nukeDescription = True
list = domain['commands'] = []
else:
if 'events' in domain:
list = domain['events']
else:
list = domain['events'] = []
if len(trimLine) == 0:
continue
item = createItem({}, match.group(1), match.group(2), match.group(4))
list.append(item)
continue
match = re.compile(r'^(experimental )?(deprecated )?domain (.*)').match(line)
if match:
domain = createItem({'domain' : match.group(3)}, match.group(1), match.group(2))
protocol['domains'].append(domain)
continue
match = re.compile(
r'^ (experimental )?(deprecated )?(optional )?'
r'(array of )?([^\s]+) ([^\s]+)').match(line)
if match:
param = createItem({}, match.group(1), match.group(2), match.group(6))
if match.group(3):
param['optional'] = True
assignType(param, match.group(5), match.group(4), map_binary_to_string)
if match.group(5) == 'enum':
enumliterals = param['enum'] = []
subitems.append(param)
continue
match = re.compile(r'^ depends on ([^\s]+)').match(line)
if match:
if 'dependencies' not in domain:
domain['dependencies'] = []
domain['dependencies'].append(match.group(1))
continue
match = re.compile(r'^ (parameters|returns|properties)').match(line)
if match:
subitems = item[match.group(1)] = []
continue
match = re.compile(r'^ (experimental )?(deprecated )?type (.*) extends (array of )?([^\s]+)').match(line)
if match:
if 'types' not in domain:
domain['types'] = []
item = createItem({'id': match.group(3)}, match.group(1), match.group(2))
assignType(item, match.group(5), match.group(4), map_binary_to_string)
domain['types'].append(item)
continue
match = re.compile(r'^ enum').match(line)
if match:
enumliterals = item['enum'] = []
continue
match = re.compile(r'^ (experimental )?(deprecated )?(command|event) (.*)').match(line)
if match:
list = []
if match.group(3) == 'command':
if 'commands' in domain:
list = domain['commands']
else:
list = domain['commands'] = []
else:
if 'events' in domain:
list = domain['events']
else:
list = domain['events'] = []
match = re.compile(r'^version').match(line)
if match:
continue
item = createItem({}, match.group(1), match.group(2), match.group(4))
list.append(item)
continue
match = re.compile(r'^ major (\d+)').match(line)
if match:
protocol['version']['major'] = match.group(1)
continue
match = re.compile(r'^ (experimental )?(deprecated )?(optional )?(array of )?([^\s]+) ([^\s]+)').match(line)
if match:
param = createItem({}, match.group(1), match.group(2), match.group(6))
if match.group(3):
param['optional'] = True
assignType(param, match.group(5), match.group(4), map_binary_to_string)
if match.group(5) == 'enum':
enumliterals = param['enum'] = []
subitems.append(param)
continue
match = re.compile(r'^ minor (\d+)').match(line)
if match:
protocol['version']['minor'] = match.group(1)
continue
match = re.compile(r'^ (parameters|returns|properties)').match(line)
if match:
subitems = item[match.group(1)] = []
continue
match = re.compile(r'^ redirect ([^\s]+)').match(line)
if match:
item['redirect'] = match.group(1)
continue
match = re.compile(r'^ enum').match(line)
if match:
enumliterals = item['enum'] = []
continue
match = re.compile(r'^ ( )?[^\s]+$').match(line)
if match:
# enum literal
enumliterals.append(trimLine)
continue
match = re.compile(r'^version').match(line)
if match:
continue
match = re.compile(r'^ major (\d+)').match(line)
if match:
protocol['version']['major'] = match.group(1)
continue
match = re.compile(r'^ minor (\d+)').match(line)
if match:
protocol['version']['minor'] = match.group(1)
continue
match = re.compile(r'^ redirect ([^\s]+)').match(line)
if match:
item['redirect'] = match.group(1)
continue
match = re.compile(r'^ ( )?[^\s]+$').match(line)
if match:
# enum literal
enumliterals.append(trimLine)
continue
print('Error in %s:%s, illegal token: \t%s' % (file_name, i, line))
sys.exit(1)
return protocol
print('Error in %s:%s, illegal token: \t%s' % (file_name, i, line))
sys.exit(1)
return protocol
def loads(data, file_name, map_binary_to_string=False):
if file_name.endswith(".pdl"):
return parse(data, file_name, map_binary_to_string)
return json.loads(data)
if file_name.endswith(".pdl"):
return parse(data, file_name, map_binary_to_string)
return json.loads(data)