From bfb98dbf5199811b0c9be4bf5d187b1c770a442e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Marjam=C3=A4ki?= Date: Wed, 21 Apr 2021 13:13:11 +0200 Subject: [PATCH] TemplateSimplifier: updated output of uninstantiated c++17 fold expressions --- lib/templatesimplifier.cpp | 35 +++++++++++++++++++++++++++++------ test/testsimplifytemplate.cpp | 8 ++++---- 2 files changed, 33 insertions(+), 10 deletions(-) diff --git a/lib/templatesimplifier.cpp b/lib/templatesimplifier.cpp index a1be04416..7e3eb1f22 100644 --- a/lib/templatesimplifier.cpp +++ b/lib/templatesimplifier.cpp @@ -3864,13 +3864,36 @@ void TemplateSimplifier::simplifyTemplates( simplify = true; if (!simplify || tok->str() != "(") continue; - if (Token::Match(tok, "( ... %op%") || - Token::Match(tok, "( %name% %op% ...") || - Token::Match(tok->link()->tokAt(-3), "%op% ... )") || - Token::Match(tok->link()->tokAt(-3), "... %op% %name% )")) { - Token::eraseTokens(tok, tok->link()); - tok->insertToken("__cppcheck_uninstantiated_fold__"); + const Token *op = nullptr; + const Token *args = nullptr; + if (Token::Match(tok, "( ... %op%")) { + op = tok->tokAt(2); + args = tok->link()->previous(); + } else if (Token::Match(tok, "( %name% %op% ...")) { + op = tok->tokAt(2); + args = tok->link()->previous()->isName() ? nullptr : tok->next(); + } else if (Token::Match(tok->link()->tokAt(-3), "%op% ... )")) { + op = tok->link()->tokAt(-2); + args = tok->next(); + } else if (Token::Match(tok->link()->tokAt(-3), "... %op% %name% )")) { + op = tok->link()->tokAt(-2); + args = tok->next()->isName() ? nullptr : tok->link()->previous(); + } else { + continue; } + + const std::string strop = op->str(); + const std::string strargs = (args && args->isName()) ? args->str() : ""; + + Token::eraseTokens(tok, tok->link()); + tok->insertToken(")"); + if (!strargs.empty()) { + tok->insertToken("..."); + tok->insertToken(strargs); + } + tok->insertToken("("); + Token::createMutualLinks(tok->next(), tok->link()->previous()); + tok->insertToken("__cppcheck_fold_" + strop + "__"); } } } diff --git a/test/testsimplifytemplate.cpp b/test/testsimplifytemplate.cpp index dc2224148..6368c40a6 100644 --- a/test/testsimplifytemplate.cpp +++ b/test/testsimplifytemplate.cpp @@ -6067,28 +6067,28 @@ private: void fold_expression_1() { const char code[] = "template bool all(Args... args) { return (... && args); }\n" "x=all(true,false,true,true);"; - const char expected[] = "template < typename ... Args > bool all ( Args ... args ) { return ( __cppcheck_uninstantiated_fold__ ) ; } x = all ( true , false , true , true ) ;"; + const char expected[] = "template < typename ... Args > bool all ( Args ... args ) { return ( __cppcheck_fold_&&__ ( args ... ) ) ; } x = all ( true , false , true , true ) ;"; ASSERT_EQUALS(expected, tok(code)); } void fold_expression_2() { const char code[] = "template bool all(Args... args) { return (args && ...); }\n" "x=all(true,false,true,true);"; - const char expected[] = "template < typename ... Args > bool all ( Args ... args ) { return ( __cppcheck_uninstantiated_fold__ ) ; } x = all ( true , false , true , true ) ;"; + const char expected[] = "template < typename ... Args > bool all ( Args ... args ) { return ( __cppcheck_fold_&&__ ( args ... ) ) ; } x = all ( true , false , true , true ) ;"; ASSERT_EQUALS(expected, tok(code)); } void fold_expression_3() { const char code[] = "template int foo(Args... args) { return (12 * ... * args); }\n" "x=foo(1,2);"; - const char expected[] = "template < typename ... Args > int foo ( Args ... args ) { return ( __cppcheck_uninstantiated_fold__ ) ; } x = foo ( 1 , 2 ) ;"; + const char expected[] = "template < typename ... Args > int foo ( Args ... args ) { return ( __cppcheck_fold_*__ ( args ... ) ) ; } x = foo ( 1 , 2 ) ;"; ASSERT_EQUALS(expected, tok(code)); } void fold_expression_4() { const char code[] = "template int foo(Args... args) { return (args * ... * 123); }\n" "x=foo(1,2);"; - const char expected[] = "template < typename ... Args > int foo ( Args ... args ) { return ( __cppcheck_uninstantiated_fold__ ) ; } x = foo ( 1 , 2 ) ;"; + const char expected[] = "template < typename ... Args > int foo ( Args ... args ) { return ( __cppcheck_fold_*__ ( args ... ) ) ; } x = foo ( 1 , 2 ) ;"; ASSERT_EQUALS(expected, tok(code)); }