From e3577f871bffac17f09a3cb201c2cd4dfca5a90a Mon Sep 17 00:00:00 2001 From: Linus Groh Date: Wed, 17 Feb 2021 22:25:51 +0100 Subject: [PATCH] LibWeb: Parse IDL interface constructors WrapperGenerator will now parse and store IDL interface constructors, including parameters and overloads. See https://heycam.github.io/webidl/#idl-constructors. --- .../CodeGenerators/WrapperGenerator.cpp | 69 ++++++++++++++----- 1 file changed, 51 insertions(+), 18 deletions(-) diff --git a/Userland/Libraries/LibWeb/CodeGenerators/WrapperGenerator.cpp b/Userland/Libraries/LibWeb/CodeGenerators/WrapperGenerator.cpp index 9f15ee4ad4..81509d2880 100644 --- a/Userland/Libraries/LibWeb/CodeGenerators/WrapperGenerator.cpp +++ b/Userland/Libraries/LibWeb/CodeGenerators/WrapperGenerator.cpp @@ -1,5 +1,6 @@ /* * Copyright (c) 2020-2021, Andreas Kling + * Copyright (c) 2021, Linus Groh * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -106,6 +107,17 @@ static void report_parsing_error(StringView message, StringView filename, String namespace IDL { +template +static size_t get_function_length(FunctionType& function) +{ + size_t length = 0; + for (auto& parameter : function.parameters) { + if (!parameter.optional) + length++; + } + return length; +} + struct Type { String name; bool nullable { false }; @@ -123,15 +135,14 @@ struct Function { Vector parameters; HashMap extended_attributes; - size_t length() const - { - size_t length = 0; - for (auto& parameter : parameters) { - if (!parameter.optional) - length++; - } - return length; - } + size_t length() const { return get_function_length(*this); } +}; + +struct Constructor { + String name; + Vector parameters; + + size_t length() const { return get_function_length(*this); } }; struct Constant { @@ -157,6 +168,7 @@ struct Interface { Vector attributes; Vector constants; + Vector constructors; Vector functions; // Added for convenience after parsing @@ -262,17 +274,11 @@ static OwnPtr parse_interface(StringView filename, const StringView& interface->constants.append(move(constant)); }; - auto parse_function = [&](HashMap& extended_attributes) { - auto return_type = parse_type(); + auto parse_parameters = [&] { consume_whitespace(); - auto name = lexer.consume_until([](auto ch) { return isspace(ch) || ch == '('; }); - consume_whitespace(); - assert_specific('('); - Vector parameters; - for (;;) { - if (lexer.consume_specific(')')) + if (lexer.next_is(')')) break; bool optional = lexer.consume_specific("optional"); if (optional) @@ -281,18 +287,40 @@ static OwnPtr parse_interface(StringView filename, const StringView& consume_whitespace(); auto name = lexer.consume_until([](auto ch) { return isspace(ch) || ch == ',' || ch == ')'; }); parameters.append({ move(type), move(name), optional }); - if (lexer.consume_specific(')')) + if (lexer.next_is(')')) break; assert_specific(','); consume_whitespace(); } + return parameters; + }; + auto parse_function = [&](HashMap& extended_attributes) { + auto return_type = parse_type(); + consume_whitespace(); + auto name = lexer.consume_until([](auto ch) { return isspace(ch) || ch == '('; }); + consume_whitespace(); + assert_specific('('); + auto parameters = parse_parameters(); + assert_specific(')'); consume_whitespace(); assert_specific(';'); interface->functions.append(Function { return_type, name, move(parameters), move(extended_attributes) }); }; + auto parse_constructor = [&] { + assert_string("constructor"); + consume_whitespace(); + assert_specific('('); + auto parameters = parse_parameters(); + assert_specific(')'); + consume_whitespace(); + assert_specific(';'); + + interface->constructors.append(Constructor { interface->name, move(parameters) }); + }; + auto parse_extended_attributes = [&] { HashMap extended_attributes; for (;;) { @@ -327,6 +355,11 @@ static OwnPtr parse_interface(StringView filename, const StringView& extended_attributes = parse_extended_attributes(); } + if (lexer.next_is("constructor")) { + parse_constructor(); + continue; + } + if (lexer.next_is("const")) { parse_constant(); continue;