From a1c275436ff52e99b90fe8c43cb153fc7ec35716 Mon Sep 17 00:00:00 2001 From: IOBYTE Date: Sat, 15 Dec 2018 01:52:47 -0500 Subject: [PATCH] Fix #8902 (Crash in TemplateSimplifier) (#1521) --- lib/templatesimplifier.cpp | 3 +-- test/testsimplifytemplate.cpp | 16 ++++++++++++++++ 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/lib/templatesimplifier.cpp b/lib/templatesimplifier.cpp index 70d5cce0f..b1c7c9326 100644 --- a/lib/templatesimplifier.cpp +++ b/lib/templatesimplifier.cpp @@ -573,7 +573,6 @@ void TemplateSimplifier::getTemplateInstantiations() mTemplateInstantiations.emplace_back(tok2->next(), getScopeName(scopeList), tok2->strAt(1), tok2->tokAt(1)); } else if (Token::Match(tok2->next(), "class|struct")) const_cast(tok2)->deleteNext(); - } // Add outer template.. @@ -1026,7 +1025,7 @@ void TemplateSimplifier::expandTemplate( } else if (copy && isFunction) { // check if this is an explicit instantiation Token * temp = templateInstantiation.token; - while (temp && !Token::Match(temp->previous(), "}|;")) + while (temp && !Token::Match(temp->previous(), "}|;|extern")) temp = temp->previous(); if (Token::Match(temp, "template !!<")) { // just delete "template" diff --git a/test/testsimplifytemplate.cpp b/test/testsimplifytemplate.cpp index 289f98bb6..8a686cad3 100644 --- a/test/testsimplifytemplate.cpp +++ b/test/testsimplifytemplate.cpp @@ -122,6 +122,7 @@ private: TEST_CASE(template82); // 8603 TEST_CASE(template83); TEST_CASE(template84); // #8880 + TEST_CASE(template85); // #8902 crash TEST_CASE(template_specialization_1); // #7868 - template specialization template struct S> {..}; TEST_CASE(template_specialization_2); // #7868 - template specialization template struct S> {..}; TEST_CASE(template_enum); // #6299 Syntax error in complex enum declaration (including template) @@ -1621,6 +1622,21 @@ private: ASSERT_EQUALS(exp, tok(code)); } + void template85() { // #8902 - crash + const char code[] = "template\n" + "struct C\n" + "{\n" + " template::value)>::type* = nullptr>\n" + " void foo();\n" + "};\n" + "extern template void C::foo();\n" + "template\n" + "template::value)>::type>\n" + "void C::foo() {}"; + // @todo the output is very wrong but we are only worried about the crash for now + tok(code); + } + void template_specialization_1() { // #7868 - template specialization template struct S> {..}; const char code[] = "template struct C {};\n" "template struct S {a};\n"