Path: blob/main/contrib/llvm-project/lldb/source/Plugins/Language/CPlusPlus/CPlusPlusNameParser.h
39644 views
//===-- CPlusPlusNameParser.h -----------------------------------*- C++ -*-===//1//2// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.3// See https://llvm.org/LICENSE.txt for license information.4// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception5//6//===----------------------------------------------------------------------===//78#ifndef LLDB_SOURCE_PLUGINS_LANGUAGE_CPLUSPLUS_CPLUSPLUSNAMEPARSER_H9#define LLDB_SOURCE_PLUGINS_LANGUAGE_CPLUSPLUS_CPLUSPLUSNAMEPARSER_H1011#include "clang/Lex/Lexer.h"12#include "llvm/ADT/SmallVector.h"13#include "llvm/ADT/StringRef.h"1415#include "lldb/Utility/ConstString.h"16#include "lldb/lldb-private.h"17#include <optional>1819namespace lldb_private {2021// Helps to validate and obtain various parts of C++ definitions.22class CPlusPlusNameParser {23public:24CPlusPlusNameParser(llvm::StringRef text) : m_text(text) { ExtractTokens(); }2526struct ParsedName {27llvm::StringRef basename;28llvm::StringRef context;29};3031struct ParsedFunction {32ParsedName name;33llvm::StringRef arguments;34llvm::StringRef qualifiers;35llvm::StringRef return_type;36};3738// Treats given text as a function definition and parses it.39// Function definition might or might not have a return type and this should40// change parsing result.41// Examples:42// main(int, chat const*)43// T fun(int, bool)44// std::vector<int>::push_back(int)45// int& map<int, pair<short, int>>::operator[](short) const46// int (*get_function(const chat *))()47std::optional<ParsedFunction> ParseAsFunctionDefinition();4849// Treats given text as a potentially nested name of C++ entity (function,50// class, field) and parses it.51// Examples:52// main53// fun54// std::vector<int>::push_back55// map<int, pair<short, int>>::operator[]56// func<C>(int, C&)::nested_class::method57std::optional<ParsedName> ParseAsFullName();5859private:60// A C++ definition to parse.61llvm::StringRef m_text;62// Tokens extracted from m_text.63llvm::SmallVector<clang::Token, 30> m_tokens;64// Index of the next token to look at from m_tokens.65size_t m_next_token_index = 0;6667// Range of tokens saved in m_next_token_index.68struct Range {69size_t begin_index = 0;70size_t end_index = 0;7172Range() = default;73Range(size_t begin, size_t end) : begin_index(begin), end_index(end) {74assert(end >= begin);75}7677size_t size() const { return end_index - begin_index; }7879bool empty() const { return size() == 0; }80};8182struct ParsedNameRanges {83Range basename_range;84Range context_range;85};8687// Bookmark automatically restores parsing position (m_next_token_index)88// when destructed unless it's manually removed with Remove().89class Bookmark {90public:91Bookmark(size_t &position)92: m_position(position), m_position_value(position) {}93Bookmark(const Bookmark &) = delete;94Bookmark(Bookmark &&b)95: m_position(b.m_position), m_position_value(b.m_position_value),96m_restore(b.m_restore) {97b.Remove();98}99Bookmark &operator=(Bookmark &&) = delete;100Bookmark &operator=(const Bookmark &) = delete;101102void Remove() { m_restore = false; }103size_t GetSavedPosition() { return m_position_value; }104~Bookmark() {105if (m_restore) {106m_position = m_position_value;107}108}109110private:111size_t &m_position;112size_t m_position_value;113bool m_restore = true;114};115116bool HasMoreTokens();117void Advance();118void TakeBack();119bool ConsumeToken(clang::tok::TokenKind kind);120121template <typename... Ts> bool ConsumeToken(Ts... kinds);122Bookmark SetBookmark();123size_t GetCurrentPosition();124clang::Token &Peek();125bool ConsumeBrackets(clang::tok::TokenKind left, clang::tok::TokenKind right);126127std::optional<ParsedFunction> ParseFunctionImpl(bool expect_return_type);128129// Parses functions returning function pointers 'string (*f(int x))(float y)'130std::optional<ParsedFunction> ParseFuncPtr(bool expect_return_type);131132// Consumes function arguments enclosed within '(' ... ')'133bool ConsumeArguments();134135// Consumes template arguments enclosed within '<' ... '>'136bool ConsumeTemplateArgs();137138// Consumes '(anonymous namespace)'139bool ConsumeAnonymousNamespace();140141// Consumes '{lambda ...}'142bool ConsumeLambda();143144// Consumes operator declaration like 'operator *' or 'operator delete []'145bool ConsumeOperator();146147// Skips 'const' and 'volatile'148void SkipTypeQualifiers();149150// Skips 'const', 'volatile', '&', '&&' in the end of the function.151void SkipFunctionQualifiers();152153// Consumes built-in types like 'int' or 'unsigned long long int'154bool ConsumeBuiltinType();155156// Consumes types defined via decltype keyword.157bool ConsumeDecltype();158159// Skips 'const' and 'volatile'160void SkipPtrsAndRefs();161162// Consumes things like 'const * const &'163bool ConsumePtrsAndRefs();164165// Consumes full type name like 'Namespace::Class<int>::Method()::InnerClass'166bool ConsumeTypename();167168/// Consumes ABI tags enclosed within '[abi:' ... ']'169///170/// Since there is no restriction on what the ABI tag171/// string may contain, this API supports parsing a small172/// set of special characters.173///174/// The following regex describes the set of supported characters:175/// [A-Za-z,.\s\d]+176bool ConsumeAbiTag();177178std::optional<ParsedNameRanges> ParseFullNameImpl();179llvm::StringRef GetTextForRange(const Range &range);180181// Populate m_tokens by calling clang lexer on m_text.182void ExtractTokens();183};184185} // namespace lldb_private186187#endif // LLDB_SOURCE_PLUGINS_LANGUAGE_CPLUSPLUS_CPLUSPLUSNAMEPARSER_H188189190