mirror of
https://github.com/RGBCube/serenity
synced 2025-05-23 18:55:08 +00:00
JSSpecCompiler: Push ParseError out of Algorithm
This commit is contained in:
parent
d339ad01bb
commit
c7369f2f93
2 changed files with 39 additions and 33 deletions
|
@ -103,38 +103,48 @@ ParseErrorOr<AlgorithmStepList> AlgorithmStepList::create(XML::Node::Element con
|
|||
return result;
|
||||
}
|
||||
|
||||
ParseErrorOr<Algorithm> Algorithm::create(XML::Node const* node)
|
||||
Optional<Algorithm> Algorithm::create(SpecificationParsingContext& ctx, XML::Node const* element)
|
||||
{
|
||||
VERIFY(node->as_element().name == tag_emu_alg);
|
||||
VERIFY(element->as_element().name == tag_emu_alg);
|
||||
|
||||
XML::Node::Element const* steps_list = nullptr;
|
||||
for (auto const& child : node->as_element().children) {
|
||||
TRY(child->content.visit(
|
||||
[&](XML::Node::Element const& element) -> ParseErrorOr<void> {
|
||||
Vector<XML::Node const*> steps_list;
|
||||
for (auto const& child : element->as_element().children) {
|
||||
child->content.visit(
|
||||
[&](XML::Node::Element const& element) {
|
||||
if (element.name == tag_ol) {
|
||||
if (steps_list != nullptr)
|
||||
return ParseError::create("<emu-alg> should have exactly one <ol> child"sv, child);
|
||||
steps_list = &element;
|
||||
return {};
|
||||
} else {
|
||||
return ParseError::create("<emu-alg> should not have children other than <ol>"sv, child);
|
||||
steps_list.append(child);
|
||||
return;
|
||||
}
|
||||
|
||||
ctx.diag().error(ctx.location_from_xml_offset(child->offset),
|
||||
"<{}> should not be a child of <emu-alg>"sv, element.name);
|
||||
},
|
||||
[&](XML::Node::Text const&) {
|
||||
if (!contains_empty_text(child)) {
|
||||
ctx.diag().error(ctx.location_from_xml_offset(child->offset),
|
||||
"non-empty text node should not be a child of <emu-alg>");
|
||||
}
|
||||
},
|
||||
[&](XML::Node::Text const&) -> ParseErrorOr<void> {
|
||||
if (!contains_empty_text(child))
|
||||
return ParseError::create("<emu-alg> should not have non-empty child text nodes"sv, child);
|
||||
return {};
|
||||
},
|
||||
move(ignore_comments)));
|
||||
[&](auto const&) {});
|
||||
}
|
||||
|
||||
if (steps_list == nullptr)
|
||||
return ParseError::create("<emu-alg> should have exactly one <ol> child"sv, node);
|
||||
if (steps_list.size() != 1) {
|
||||
ctx.diag().error(ctx.location_from_xml_offset(element->offset),
|
||||
"<emu-alg> should have exactly one <ol> child"sv);
|
||||
return {};
|
||||
}
|
||||
|
||||
auto steps_creation_result = AlgorithmStepList::create(steps_list[0]->as_element());
|
||||
if (steps_creation_result.is_error()) {
|
||||
// TODO: Integrate backtracing parser errors better
|
||||
ctx.diag().error(ctx.location_from_xml_offset(steps_creation_result.error()->offset()),
|
||||
"{}", steps_creation_result.error()->to_string());
|
||||
return {};
|
||||
}
|
||||
|
||||
Algorithm algorithm;
|
||||
algorithm.m_steps = TRY(AlgorithmStepList::create(*steps_list));
|
||||
algorithm.m_steps = steps_creation_result.release_value();
|
||||
algorithm.m_tree = algorithm.m_steps.m_expression;
|
||||
|
||||
return algorithm;
|
||||
}
|
||||
|
||||
|
@ -278,21 +288,17 @@ bool SpecFunction::post_initialize(SpecificationParsingContext& ctx, XML::Node c
|
|||
|
||||
if (algorithm_nodes.size() != 1) {
|
||||
ctx.diag().error(ctx.location_from_xml_offset(element->offset),
|
||||
"<emu-clause> specifing function should have exactly one <emu-alg>"sv);
|
||||
"<emu-clause> specifing function should have exactly one <emu-alg> child"sv);
|
||||
return false;
|
||||
}
|
||||
|
||||
auto algorithm_creation_result = Algorithm::create(algorithm_nodes[0]);
|
||||
if (algorithm_creation_result.is_error()) {
|
||||
// TODO: Integrate backtracing parser errors better
|
||||
ctx.diag().error(ctx.location_from_xml_offset(algorithm_creation_result.error()->offset()),
|
||||
"{}", algorithm_creation_result.error()->to_string());
|
||||
auto maybe_algorithm = Algorithm::create(ctx, algorithm_nodes[0]);
|
||||
if (maybe_algorithm.has_value()) {
|
||||
m_algorithm = maybe_algorithm.release_value();
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
|
||||
m_algorithm = algorithm_creation_result.release_value();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void SpecFunction::do_collect(TranslationUnitRef translation_unit)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue