mirror of
https://github.com/SerenityOS/serenity
synced 2024-10-16 21:04:20 +00:00
LibCpp: Add "ignore invalid statements" option to Preprocessor
When we run the Preprocessor from the CppComprehensionEngine of the language server, we don't want the preprocessor to crash if it encounters an invalid preprocessor statement (for example, an #endif statement without an accompanying previous #if statement). To achieve this, this commit adds an "ignore_invalid_statements" flag to the preprocessor which is set by the CppComprehensionEngine. Fixes #11064.
This commit is contained in:
parent
408f05bbb9
commit
c3c2fe153b
|
@ -574,6 +574,7 @@ OwnPtr<CppComprehensionEngine::DocumentData> CppComprehensionEngine::create_docu
|
|||
document_data->m_text = move(text);
|
||||
document_data->m_preprocessor = make<Preprocessor>(document_data->m_filename, document_data->text());
|
||||
document_data->preprocessor().set_ignore_unsupported_keywords(true);
|
||||
document_data->preprocessor().set_ignore_invalid_statements(true);
|
||||
document_data->preprocessor().set_keep_include_statements(true);
|
||||
|
||||
document_data->preprocessor().definitions_in_header_callback = [this](StringView include_path) -> Preprocessor::Definitions {
|
||||
|
|
|
@ -117,6 +117,8 @@ void Preprocessor::handle_preprocessor_keyword(StringView keyword, GenericLexer&
|
|||
}
|
||||
|
||||
if (keyword == "else") {
|
||||
if (m_options.ignore_invalid_statements && m_current_depth == 0)
|
||||
return;
|
||||
VERIFY(m_current_depth > 0);
|
||||
if (m_depths_of_not_taken_branches.contains_slow(m_current_depth - 1)) {
|
||||
m_depths_of_not_taken_branches.remove_all_matching([this](auto x) { return x == m_current_depth - 1; });
|
||||
|
@ -129,6 +131,8 @@ void Preprocessor::handle_preprocessor_keyword(StringView keyword, GenericLexer&
|
|||
}
|
||||
|
||||
if (keyword == "endif") {
|
||||
if (m_options.ignore_invalid_statements && m_current_depth == 0)
|
||||
return;
|
||||
VERIFY(m_current_depth > 0);
|
||||
--m_current_depth;
|
||||
if (m_depths_of_not_taken_branches.contains_slow(m_current_depth)) {
|
||||
|
@ -198,6 +202,8 @@ void Preprocessor::handle_preprocessor_keyword(StringView keyword, GenericLexer&
|
|||
}
|
||||
|
||||
if (keyword == "elif") {
|
||||
if (m_options.ignore_invalid_statements && m_current_depth == 0)
|
||||
return;
|
||||
VERIFY(m_current_depth > 0);
|
||||
// FIXME: Evaluate the elif expression
|
||||
// We currently always treat the expression in #elif as true.
|
||||
|
|
|
@ -44,6 +44,7 @@ public:
|
|||
Vector<Substitution> const& substitutions() const { return m_substitutions; }
|
||||
|
||||
void set_ignore_unsupported_keywords(bool ignore) { m_options.ignore_unsupported_keywords = ignore; }
|
||||
void set_ignore_invalid_statements(bool ignore) { m_options.ignore_invalid_statements = ignore; }
|
||||
void set_keep_include_statements(bool keep) { m_options.keep_include_statements = keep; }
|
||||
|
||||
Function<Definitions(StringView)> definitions_in_header_callback { nullptr };
|
||||
|
@ -91,6 +92,7 @@ private:
|
|||
|
||||
struct Options {
|
||||
bool ignore_unsupported_keywords { false };
|
||||
bool ignore_invalid_statements { false };
|
||||
bool keep_include_statements { false };
|
||||
} m_options;
|
||||
};
|
||||
|
|
Loading…
Reference in a new issue