From 30e7a1b2b34d14d533630a35abc0cd64b397fbba Mon Sep 17 00:00:00 2001 From: Yingchi Long Date: Thu, 18 Apr 2024 11:01:51 +0800 Subject: [PATCH] libnixf: support parsing extra dot after attrpath (#428) --- libnixf/include/nixf/Basic/Nodes/Attrs.h | 11 ++++++++--- libnixf/src/Parse/ParseAttrs.cpp | 5 ++++- libnixf/src/Sema/SemaActions.cpp | 3 ++- 3 files changed, 14 insertions(+), 5 deletions(-) diff --git a/libnixf/include/nixf/Basic/Nodes/Attrs.h b/libnixf/include/nixf/Basic/Nodes/Attrs.h index cb9b398c2..ec0d9f4ae 100644 --- a/libnixf/include/nixf/Basic/Nodes/Attrs.h +++ b/libnixf/include/nixf/Basic/Nodes/Attrs.h @@ -89,10 +89,14 @@ class AttrName : public Node { class AttrPath : public Node { const std::vector> Names; + // FIXME: workaround for just recording the trailing dot. + const std::shared_ptr TrailingDot; public: - AttrPath(LexerCursorRange Range, std::vector> Names) - : Node(NK_AttrPath, Range), Names(std::move(Names)) {} + AttrPath(LexerCursorRange Range, std::vector> Names, + std::shared_ptr TrailingDot) + : Node(NK_AttrPath, Range), Names(std::move(Names)), + TrailingDot(std::move(TrailingDot)) {} [[nodiscard]] const std::vector> &names() const { return Names; @@ -100,10 +104,11 @@ class AttrPath : public Node { [[nodiscard]] ChildVector children() const override { ChildVector Children; - Children.reserve(Names.size()); + Children.reserve(Names.size() + 1); for (const auto &Name : Names) { Children.push_back(Name.get()); } + Children.emplace_back(TrailingDot.get()); return Children; } }; diff --git a/libnixf/src/Parse/ParseAttrs.cpp b/libnixf/src/Parse/ParseAttrs.cpp index 01a6a9b48..bd025756b 100644 --- a/libnixf/src/Parse/ParseAttrs.cpp +++ b/libnixf/src/Parse/ParseAttrs.cpp @@ -36,6 +36,7 @@ std::shared_ptr Parser::parseAttrPath() { assert(LastToken && "LastToken should be set after valid attrname"); std::vector> AttrNames; AttrNames.emplace_back(std::move(First)); + std::shared_ptr TrailingDot; while (true) { if (Token Tok = peek(); Tok.kind() == tok_dot) { consume(); @@ -47,6 +48,7 @@ std::shared_ptr Parser::parseAttrPath() { D.fix("remove extra .").edit(TextEdit::mkRemoval(Tok.range())); D.fix("insert dummy attrname") .edit(TextEdit::mkInsertion(Tok.rCur(), R"("dummy")")); + TrailingDot = std::make_shared(Tok.range()); continue; } AttrNames.emplace_back(std::move(Next)); @@ -55,7 +57,8 @@ std::shared_ptr Parser::parseAttrPath() { break; } return std::make_shared(LexerCursorRange{Begin, LastToken->rCur()}, - std::move(AttrNames)); + std::move(AttrNames), + std::move(TrailingDot)); } std::shared_ptr Parser::parseBinding() { diff --git a/libnixf/src/Sema/SemaActions.cpp b/libnixf/src/Sema/SemaActions.cpp index 206a6915c..22546b7d2 100644 --- a/libnixf/src/Sema/SemaActions.cpp +++ b/libnixf/src/Sema/SemaActions.cpp @@ -330,7 +330,8 @@ std::shared_ptr Sema::desugarInheritExpr(std::shared_ptr Name, return std::make_shared(Range, Name->id()); auto Path = std::make_shared( - Range, std::vector>{std::move(Name)}); + Range, std::vector>{std::move(Name)}, + /*TrailingDot=*/nullptr); return std::make_shared(Range, std::move(E), std::move(Path), nullptr); }