[ Web Proxy ]
URL:
Viewing: https://raw.githubusercontent.com/napcode/cppcheck/master/test/testvarid.cpp [Back]  [Original]

/*
 * Cppcheck - A tool for static C/C++ code analysis
 * Copyright (C) 2007-2019 Cppcheck team.
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see .
 */

#include "platform.h"
#include "settings.h"
#include "standards.h"
#include "testsuite.h"
#include "token.h"
#include "tokenize.h"

#include 

struct InternalError;


class TestVarID : public TestFixture {
public:
    TestVarID() : TestFixture("TestVarID") {
    }

private:
    void run() OVERRIDE {
        TEST_CASE(varid1);
        TEST_CASE(varid2);
        TEST_CASE(varid3);
        TEST_CASE(varid4);
        TEST_CASE(varid5);
        TEST_CASE(varid6);
        TEST_CASE(varid7);
        TEST_CASE(varidReturn1);
        TEST_CASE(varidReturn2);
        TEST_CASE(varid8);
        TEST_CASE(varid9);
        TEST_CASE(varid10);
        TEST_CASE(varid11);
        TEST_CASE(varid12);
        TEST_CASE(varid13);
        TEST_CASE(varid14);
        TEST_CASE(varid15);
        TEST_CASE(varid16);
        TEST_CASE(varid17);   // ticket #1810
        TEST_CASE(varid18);
        TEST_CASE(varid19);
        TEST_CASE(varid20);
        TEST_CASE(varid24);
        TEST_CASE(varid25);
        TEST_CASE(varid26);   // ticket #1967 (list of function pointers)
        TEST_CASE(varid27);   // Ticket #2280 (same name for namespace and variable)
        TEST_CASE(varid28);   // ticket #2630
        TEST_CASE(varid29);   // ticket #1974
        TEST_CASE(varid30);   // ticket #2614
        TEST_CASE(varid34);   // ticket #2825
        TEST_CASE(varid35);   // function declaration inside function body
        TEST_CASE(varid36);   // ticket #2980 (segmentation fault)
        TEST_CASE(varid37);   // ticket #3092 (varid for 'Bar bar(*this);')
        TEST_CASE(varid38);   // ticket #3272 (varid for 'FOO class C;')
        TEST_CASE(varid39);   // ticket #3279 (varid for 'FOO::BAR const')
        TEST_CASE(varid40);   // ticket #3279
        TEST_CASE(varid41);   // ticket #3340 (varid for union type)
        TEST_CASE(varid42);   // ticket #3316 (varid for array)
        TEST_CASE(varid43);
        TEST_CASE(varid44);
        TEST_CASE(varid45); // #3466
        TEST_CASE(varid46); // struct varname
        TEST_CASE(varid47); // function parameters
        TEST_CASE(varid48); // #3785 - return (a*b)
        TEST_CASE(varid49); // #3799 - void f(std::vector)
        TEST_CASE(varid50); // #3760 - explicit
        TEST_CASE(varid51); // don't set varid for template function
        TEST_CASE(varid52); // Set varid for nested templates
        TEST_CASE(varid53); // #4172 - Template instantiation: T list[4];
        TEST_CASE(varid54); // hang
        TEST_CASE(varid55); // #5868: Function::addArgument with varid 0 for argument named the same as a typedef
        TEST_CASE(varid56); // function with a throw()
        TEST_CASE(varid57); // #6636: new scope by {}
        TEST_CASE(varid58); // #6638: for loop in for condition
        TEST_CASE(varid59); // #6696
        TEST_CASE(varid60); // #7267 cast '(unsigned x)10'
        TEST_CASE(varid61); // #4988 inline function
        TEST_CASE(varid62);
        TEST_CASE(varid63);
        TEST_CASE(varid_cpp_keywords_in_c_code);
        TEST_CASE(varid_cpp_keywords_in_c_code2); // #5373: varid=0 for argument called "delete"
        TEST_CASE(varidFunctionCall1);
        TEST_CASE(varidFunctionCall2);
        TEST_CASE(varidFunctionCall3);
        TEST_CASE(varidFunctionCall4);  // ticket #3280
        TEST_CASE(varidFunctionCall5);
        TEST_CASE(varidStl);
        TEST_CASE(varidStl2);
        TEST_CASE(varid_newauto);       // not declaration: new const auto(0);
        TEST_CASE(varid_delete);
        TEST_CASE(varid_functions);
        TEST_CASE(varid_sizeof);
        TEST_CASE(varid_reference_to_containers);
        TEST_CASE(varid_in_class1);
        TEST_CASE(varid_in_class2);
        TEST_CASE(varid_in_class3);     // #3092 - shadow variable in member function
        TEST_CASE(varid_in_class4);     // #3271 - public: class C;
        TEST_CASE(varid_in_class5);     // #3584 - std::vector b;
        TEST_CASE(varid_in_class6);     // #3755
        TEST_CASE(varid_in_class7);     // set variable id for struct members
        TEST_CASE(varid_in_class9);     // #4291 - id for variables accessed through 'this'
        TEST_CASE(varid_in_class10);
        TEST_CASE(varid_in_class11);    // #4277 - anonymous union
        TEST_CASE(varid_in_class12);    // #4637 - method
        TEST_CASE(varid_in_class13);    // #4637 - method
        TEST_CASE(varid_in_class14);
        TEST_CASE(varid_in_class15);    // #5533 - functions
        TEST_CASE(varid_in_class16);
        TEST_CASE(varid_in_class17);    // #6056 - no varid for member functions
        TEST_CASE(varid_in_class18);    // #7127
        TEST_CASE(varid_in_class19);
        TEST_CASE(varid_in_class20);    // #7267
        TEST_CASE(varid_in_class21);    // #7788
        TEST_CASE(varid_namespace_1);   // #7272
        TEST_CASE(varid_namespace_2);   // #7000
        TEST_CASE(varid_namespace_3);   // #8627
        TEST_CASE(varid_initList);
        TEST_CASE(varid_initListWithBaseTemplate);
        TEST_CASE(varid_initListWithScope);
        TEST_CASE(varid_operator);
        TEST_CASE(varid_throw);
        TEST_CASE(varid_unknown_macro);     // #2638 - unknown macro is not type
        TEST_CASE(varid_using);  // ticket #3648
        TEST_CASE(varid_catch);
        TEST_CASE(varid_functionPrototypeTemplate);
        TEST_CASE(varid_templatePtr); // #4319
        TEST_CASE(varid_templateNamespaceFuncPtr); // #4172
        TEST_CASE(varid_templateArray);
        TEST_CASE(varid_templateParameter); // #7046 set varid for "X":  std::array Y;
        TEST_CASE(varid_templateUsing); // #5781 #7273
        TEST_CASE(varid_not_template_in_condition); // #7988
        TEST_CASE(varid_cppcast); // #6190
        TEST_CASE(varid_variadicFunc);
        TEST_CASE(varid_typename); // #4644
        TEST_CASE(varid_rvalueref);
        TEST_CASE(varid_arrayFuncPar); // #5294
        TEST_CASE(varid_sizeofPassed); // #5295
        TEST_CASE(varid_classInFunction); // #5293
        TEST_CASE(varid_pointerToArray); // #2645
        TEST_CASE(varid_cpp11initialization); // #4344
        TEST_CASE(varid_inheritedMembers); // #4101
        TEST_CASE(varid_header); // #6386
        TEST_CASE(varid_rangeBasedFor);
        TEST_CASE(varid_structinit); // #6406
        TEST_CASE(varid_arrayinit); // #7579
        TEST_CASE(varid_lambda_arg);
        TEST_CASE(varid_lambda_mutable);
        TEST_CASE(varid_trailing_return1); // #8889
        TEST_CASE(varid_trailing_return2); // #9066
        TEST_CASE(varid_parameter_pack); // #9383

        TEST_CASE(varidclass1);
        TEST_CASE(varidclass2);
        TEST_CASE(varidclass3);
        TEST_CASE(varidclass4);
        TEST_CASE(varidclass5);
        TEST_CASE(varidclass6);
        TEST_CASE(varidclass7);
        TEST_CASE(varidclass8);
        TEST_CASE(varidclass9);
        TEST_CASE(varidclass10);  // variable declaration below usage
        TEST_CASE(varidclass11);  // variable declaration below usage
        TEST_CASE(varidclass12);
        TEST_CASE(varidclass13);
        TEST_CASE(varidclass14);
        TEST_CASE(varidclass15);  // initializer list
        TEST_CASE(varidclass16);  // #4577
        TEST_CASE(varidclass17);  // #6073
        TEST_CASE(varidclass18);
        TEST_CASE(varidclass19);  // initializer list
        TEST_CASE(varid_classnameshaddowsvariablename); // #3990

        TEST_CASE(varidnamespace1);
        TEST_CASE(varidnamespace2);
        TEST_CASE(usingNamespace1);
        TEST_CASE(usingNamespace2);
        TEST_CASE(usingNamespace3);

        TEST_CASE(setVarIdStructMembers1);

        TEST_CASE(decltype1);
    }

    std::string tokenize(const char code[], bool simplify = false, const char filename[] = "test.cpp") {
        errout.str("");

        Settings settings;
        settings.platform(Settings::Unix64);
        settings.standards.c   = Standards::C89;
        settings.standards.cpp = Standards::CPP11;

        Tokenizer tokenizer(&settings, this);
        std::istringstream istr(code);
        tokenizer.tokenize(istr, filename);

        if (simplify)
            tokenizer.simplifyTokenList2();

        // result..
        return tokenizer.tokens()->stringifyList(true,true,true,true,false);
    }

    std::string compareVaridsForVariable(const char code[], const char varname[], const char filename[] = "test.cpp") {
        errout.str("");

        Settings settings;
        settings.platform(Settings::Unix64);
        settings.standards.c   = Standards::C89;
        settings.standards.cpp = Standards::CPP11;

        Tokenizer tokenizer(&settings, this);
        std::istringstream istr(code);
        tokenizer.tokenize(istr, filename);

        unsigned int varid = ~0U;
        for (const Token *tok = tokenizer.tokens(); tok; tok = tok->next()) {
            if (tok->str() == varname) {
                if (varid == ~0U)
                    varid = tok->varId();
                else if (varid != tok->varId())
                    return std::string("Variable ") + varname + " has different varids:\n" + tokenizer.tokens()->stringifyList(true,true,true,true,false);
            }
        }

        return "same varid";
    }

    void varid1() {
        {
            const std::string actual = tokenize(
                                           "static int i = 1;\n"
                                           "void f()\n"
                                           "{\n"
                                           "    int i = 2;\n"
                                           "    for (int i = 0; i < 10; ++i)\n"
                                           "        i = 3;\n"
                                           "    i = 4;\n"
                                           "}\n", false, "test.c");

            const char expected[] = "1: static int i@1 = 1 ;\n"
                                    "2: void f ( )\n"
                                    "3: {\n"
                                    "4: int i@2 ; i@2 = 2 ;\n"
                                    "5: for ( int i@3 = 0 ; i@3 < 10 ; ++ i@3 ) {\n"
                                    "6: i@3 = 3 ; }\n"
                                    "7: i@2 = 4 ;\n"
                                    "8: }\n";

            ASSERT_EQUALS(expected, actual);
        }

        {
            const std::string actual = tokenize(
                                           "static int i = 1;\n"
                                           "void f()\n"
                                           "{\n"
                                           "    int i = 2;\n"
                                           "    for (int i = 0; i < 10; ++i)\n"
                                           "    {\n"
                                           "      i = 3;\n"
                                           "    }\n"
                                           "    i = 4;\n"
                                           "}\n", false, "test.c");

            const char expected[] = "1: static int i@1 = 1 ;\n"
                                    "2: void f ( )\n"
                                    "3: {\n"
                                    "4: int i@2 ; i@2 = 2 ;\n"
                                    "5: for ( int i@3 = 0 ; i@3 < 10 ; ++ i@3 )\n"
                                    "6: {\n"
                                    "7: i@3 = 3 ;\n"
                                    "8: }\n"
                                    "9: i@2 = 4 ;\n"
                                    "10: }\n";

            ASSERT_EQUALS(expected, actual);
        }
    }

    void varid2() {
        const std::string actual = tokenize(
                                       "void f()\n"
                                       "{\n"
                                       "    struct ABC abc;\n"
                                       "    abc.a = 3;\n"
                                       "    i = abc.a;\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: void f ( )\n"
                                "2: {\n"
                                "3: struct ABC abc@1 ;\n"
                                "4: abc@1 . a@2 = 3 ;\n"
                                "5: i = abc@1 . a@2 ;\n"
                                "6: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varid3() {
        const std::string actual = tokenize(
                                       "static char str[4];\n"
                                       "void f()\n"
                                       "{\n"
                                       "    char str[10];\n"
                                       "    str[0] = 0;\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: static char str@1 [ 4 ] ;\n"
                                "2: void f ( )\n"
                                "3: {\n"
                                "4: char str@2 [ 10 ] ;\n"
                                "5: str@2 [ 0 ] = 0 ;\n"
                                "6: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varid4() {
        const std::string actual = tokenize(
                                       "void f(const unsigned int a[])\n"
                                       "{\n"
                                       "    int i = *(a+10);\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: void f ( const unsigned int a@1 [ ] )\n"
                                "2: {\n"
                                "3: int i@2 ; i@2 = * ( a@1 + 10 ) ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varid5() {
        const std::string actual = tokenize(
                                       "void f()\n"
                                       "{\n"
                                       "    int a,b;\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: void f ( )\n"
                                "2: {\n"
                                "3: int a@1 ; int b@2 ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, actual);
    }


    void varid6() {
        const std::string actual = tokenize(
                                       "int f(int a, int b)\n"
                                       "{\n"
                                       "    return a+b;\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: int f ( int a@1 , int b@2 )\n"
                                "2: {\n"
                                "3: return a@1 + b@2 ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, actual);
    }


    void varid7() {
        const std::string actual = tokenize(
                                       "void func() {\n"
                                       "    char a[256] = \"test\";\n"
                                       "    {\n"
                                       "        char b[256] = \"test\";\n"
                                       "    }\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: void func ( ) {\n"
                                "2: char a@1 [ 256 ] = \"test\" ;\n"
                                "3: {\n"
                                "4: char b@2 [ 256 ] = \"test\" ;\n"
                                "5: }\n"
                                "6: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varidReturn1() {
        const std::string actual = tokenize(
                                       "int f()\n"
                                       "{\n"
                                       "    int a;\n"
                                       "    return a;\n"
                                       "}\n", false, "test.c");

        const char expected[] = "1: int f ( )\n"
                                "2: {\n"
                                "3: int a@1 ;\n"
                                "4: return a@1 ;\n"
                                "5: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varidReturn2() {
        const std::string actual = tokenize(
                                       "void foo()\n"
                                       "{\n"
                                       "    unsigned long mask = (1UL  x@1 ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid20() {
        const char code[] ="void foo()\n"
                           "{\n"
                           "    pair x;\n"
                           "}\n";

        const char expected[] = "1: void foo ( )\n"
                                "2: {\n"
                                "3: pair < vector < int > , vector < double > > x@1 ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid24() {
        const char code[] ="class foo()\n"
                           "{\n"
                           "public:\n"
                           "    ;\n"
                           "private:\n"
                           "    static int i;\n"
                           "};\n";

        const char expected[] = "1: class foo ( )\n"
                                "2: {\n"
                                "3: public:\n"
                                "4: ;\n"
                                "5: private:\n"
                                "6: static int i@1 ;\n"
                                "7: } ;\n";

        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid25() {
        const char code[] ="class foo()\n"
                           "{\n"
                           "public:\n"
                           "    ;\n"
                           "private:\n"
                           "    mutable int i;\n"
                           "};\n";

        const char expected[] = "1: class foo ( )\n"
                                "2: {\n"
                                "3: public:\n"
                                "4: ;\n"
                                "5: private:\n"
                                "6: mutable int i@1 ;\n"
                                "7: } ;\n";

        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid26() {
        const char code[] ="list functions;\n";
        const char expected[] = "1: list < int ( * ) ( ) > functions@1 ;\n";
        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid27() {
        const char code[] ="int fooled_ya;\n"
                           "fooled_ya::iterator iter;\n";
        const char expected[] = "1: int fooled_ya@1 ;\n"
                                "2: fooled_ya :: iterator iter@2 ;\n";
        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid28() { // ticket #2630 (segmentation fault)
        ASSERT_THROW(tokenize("template \n"), InternalError);
    }

    void varid29() {
        const char code[] ="class A {\n"
                           "    B b;\n"
                           "};\n";
        const char expected[] = "1: class A {\n"
                                "2: B < C < 1 > , 1 > b@1 ;\n"
                                "3: } ;\n";
        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varid30() { // ticket #2614
        const char code1[] = "void f(EventPtr *eventP, ActionPtr **actionsP)\n"
                             "{\n"
                             "    EventPtr event = *eventP;\n"
                             "    *actionsP = &event->actions;\n"
                             "}\n";
        const char expected1[] = "1: void f ( EventPtr * eventP@1 , ActionPtr * * actionsP@2 )\n"
                                 "2: {\n"
                                 "3: EventPtr event@3 ; event@3 = * eventP@1 ;\n"
                                 "4: * actionsP@2 = & event@3 . actions@4 ;\n"
                                 "5: }\n";
        ASSERT_EQUALS(expected1, tokenize(code1, false, "test.c"));

        const char code2[] = "void f(int b, int c) {\n"
                             "    x(a*b*c,10);\n"
                             "}\n";
        const char expected2[] = "1: void f ( int b@1 , int c@2 ) {\n"
                                 "2: x ( a * b@1 * c@2 , 10 ) ;\n"
                                 "3: }\n";
        ASSERT_EQUALS(expected2, tokenize(code2, false, "test.c"));

        const char code3[] = "class Nullpointer : public ExecutionPath\n"
                             " {\n"
                             "    Nullpointer(Check *c, const unsigned int id, const std::string &name)\n"
                             "        : ExecutionPath(c, id)\n"
                             "    {\n"
                             "    }\n"
                             "}\n";
        const char expected3[] = "1: class Nullpointer : public ExecutionPath\n"
                                 "2: {\n"
                                 "3: Nullpointer ( Check * c@1 , const unsigned int id@2 , const std :: string & name@3 )\n"
                                 "4: : ExecutionPath ( c@1 , id@2 )\n"
                                 "5: {\n"
                                 "6: }\n"
                                 "7: }\n";
        ASSERT_EQUALS(expected3, tokenize(code3));
    }

    void varid34() { // ticket #2825
        const char code[] ="class Fred : public B1, public B2\n"
                           "{\n"
                           "public:\n"
                           "    Fred() { a = 0; }\n"
                           "private:\n"
                           "    int a;\n"
                           "};\n";
        const char expected[] = "1: class Fred : public B1 , public B2\n"
                                "2: {\n"
                                "3: public:\n"
                                "4: Fred ( ) { a@1 = 0 ; }\n"
                                "5: private:\n"
                                "6: int a@1 ;\n"
                                "7: } ;\n";
        ASSERT_EQUALS(expected, tokenize(code));
        ASSERT_EQUALS("", errout.str());
    }

    void varid35() { // function declaration inside function body
        // #2937
        const char code[] ="int foo() {\n"
                           "    int f(x);\n"
                           "    return f;\n"
                           "}\n";
        const char expected[] = "1: int foo ( ) {\n"
                                "2: int f@1 ( x ) ;\n"
                                "3: return f@1 ;\n"
                                "4: }\n";
        ASSERT_EQUALS(expected, tokenize(code));

        // #4627
        const char code2[] = "void f() {\n"
                             "  int  *p;\n"
                             "  void bar(int *p);\n"
                             "}";
        const char expected2[] = "1: void f ( ) {\n"
                                 "2: int * p@1 ;\n"
                                 "3: void bar ( int * p ) ;\n"
                                 "4: }\n";
        ASSERT_EQUALS(expected2, tokenize(code2));

        // #7740
        const char code3[] = "Float f(float scale) {\n"
                             "    return Float(val * scale);\n"
                             "}\n";
        const char expected3[] = "1: Float f ( float scale@1 ) {\n"
                                 "2: return Float ( val * scale@1 ) ;\n"
                                 "3: }\n";
        ASSERT_EQUALS(expected3, tokenize(code3));
    }

    void varid36() { // ticket #2980 (segmentation fault)
        const char code[] ="#elif A\n"
                           "A,a )\n",
                      tokenize(code, false, "test.cpp"));
    }

    void varid50() {  // #3760 - explicit
        const char code[] ="class A { explicit A(const A&); };";
        ASSERT_EQUALS("1: class A { explicit A ( const A & ) ; } ;\n",
                      tokenize(code, false, "test.cpp"));
    }

    void varid51() {  // don't set varid on template function
        const char code[] ="T t; t.x();";
        ASSERT_EQUALS("1: T t@1 ; t@1 . x < 0 > ( ) ;\n",
                      tokenize(code, false, "test.cpp"));
    }

    void varid52() {
        const char code[] ="A e;\n"
                           "B< C > b[10];\n"
                           "B c[10];";
        ASSERT_EQUALS("1: A < B < C > :: D > e@1 ;\n"
                      "2: B < C < > > b@2 [ 10 ] ;\n"
                      "3: B < C < > > c@3 [ 10 ] ;\n",
                      tokenize(code, false, "test.cpp"));
    }

    void varid53() { // #4172 - Template instantiation: T list[4];
        ASSERT_EQUALS("1: A < & f > list@1 [ 4 ] ;\n",
                      tokenize("A list[4];", false, "test.cpp"));
    }

    void varid54() { // hang
        // Original source code: libgc
        tokenize("STATIC ptr_t GC_approx_sp(void) { word sp; sp = (word)&sp; return((ptr_t)sp); }",true);
    }

    void varid55() { // Ticket #5868
        const char code[] =     "typedef struct foo {} foo; "
                                "void bar1(struct foo foo) {} "
                                "void baz1(foo foo) {} "
                                "void bar2(struct foo& foo) {} "
                                "void baz2(foo& foo) {} "
                                "void bar3(struct foo* foo) {} "
                                "void baz3(foo* foo) {}";
        const char expected[] = "1: "
                                "struct foo { } ; "
                                "void bar1 ( struct foo foo@1 ) { } "
                                "void baz1 ( struct foo foo@2 ) { } "
                                "void bar2 ( struct foo & foo@3 ) { } "
                                "void baz2 ( struct foo & foo@4 ) { } "
                                "void bar3 ( struct foo * foo@5 ) { } "
                                "void baz3 ( struct foo * foo@6 ) { }\n";
        ASSERT_EQUALS(expected, tokenize(code, false, "test.cpp"));
    }

    void varid56() { // Ticket #6548 - function with a throw()
        const char code1[] = "void fred(int x) throw() {}"
                             "void wilma() { x++; }";
        const char expected1[] = "1: "
                                 "void fred ( int x@1 ) throw ( ) { } "
                                 "void wilma ( ) { x ++ ; }\n";
        ASSERT_EQUALS(expected1, tokenize(code1, false, "test.cpp"));

        const char code2[] = "void fred(int x) const throw(EXCEPT) {}"
                             "void wilma() { x++; }";
        const char expected2[] = "1: "
                                 "void fred ( int x@1 ) const throw ( EXCEPT ) { } "
                                 "void wilma ( ) { x ++ ; }\n";
        ASSERT_EQUALS(expected2, tokenize(code2, false, "test.cpp"));

        const char code3[] = "void fred(int x) throw() ABCD {}"
                             "void wilma() { x++; }";
        const char expected3[] = "1: "
                                 "void fred ( int x@1 ) throw ( ) { } "
                                 "void wilma ( ) { x ++ ; }\n";
        ASSERT_EQUALS(expected3, tokenize(code3, false, "test.cpp"));

        const char code4[] = "void fred(int x) noexcept() {}"
                             "void wilma() { x++; }";
        const char expected4[] = "1: "
                                 "void fred ( int x@1 ) noexcept ( ) { } "
                                 "void wilma ( ) { x ++ ; }\n";
        ASSERT_EQUALS(expected4, tokenize(code4, false, "test.cpp"));

        const char code5[] = "void fred(int x) noexcept {}"
                             "void wilma() { x++; }";
        const char expected5[] = "1: "
                                 "void fred ( int x@1 ) noexcept ( true ) { } "
                                 "void wilma ( ) { x ++ ; }\n";
        ASSERT_EQUALS(expected5, tokenize(code5, false, "test.cpp"));

        const char code6[] = "void fred(int x) noexcept ( false ) {}"
                             "void wilma() { x++; }";
        const char expected6[] = "1: "
                                 "void fred ( int x@1 ) noexcept ( false ) { } "
                                 "void wilma ( ) { x ++ ; }\n";
        ASSERT_EQUALS(expected6, tokenize(code6, false, "test.cpp"));
    }

    void varid57() { // #6636: new scope by {}
        const char code1[] = "void SmoothPath() {\n"
                             "    {\n" // new scope
                             "        float dfx = (p2p0.x > 0.0f)?\n"
                             "                    ((n0->xmax() * SQUARE_SIZE) - p0.x):\n"
                             "                    ((n0->xmin() * SQUARE_SIZE) - p0.x);\n"
                             "        float tx = dfx / dx;\n"
                             "        if (hEdge) {\n"
                             "        }\n"
                             "        if (vEdge) {\n"
                             "            pi.z = tx;\n"
                             "        }\n"
                             "    }\n"
                             "}\n";
        const char expected1[] = "1: void SmoothPath ( ) {\n"
                                 "2:\n"
                                 "3: float dfx@1 ; dfx@1 = ( p2p0 . x > 0.0f ) ?\n"
                                 "4: ( ( n0 . xmax ( ) * SQUARE_SIZE ) - p0 . x ) :\n"
                                 "5: ( ( n0 . xmin ( ) * SQUARE_SIZE ) - p0 . x ) ;\n"
                                 "6: float tx@2 ; tx@2 = dfx@1 / dx ;\n"
                                 "7: if ( hEdge ) {\n"
                                 "8: }\n"
                                 "9: if ( vEdge ) {\n"
                                 "10: pi . z = tx@2 ;\n"
                                 "11: }\n"
                                 "12:\n"
                                 "13: }\n";
        ASSERT_EQUALS(expected1, tokenize(code1, false, "test.cpp"));
    }

    void varid58() { // #6638: for loop in for condition
        const char code1[] = "void f() {\n"
                             "    for (int i;\n"
                             "         ({for(int i;i;++i){i++;}i++;}),i;\n"
                             "         ({for(int i;i;++i){i++;}i++;}),i++) {\n"
                             "         i++;\n"
                             "    }\n"
                             "}\n";
        const char expected1[] = "1: void f ( ) {\n"
                                 "2: for ( int i@1 ;\n"
                                 "3: ( { for ( int i@2 ; i@2 ; ++ i@2 ) { i@2 ++ ; } i@1 ++ ; } ) , i@1 ;\n"
                                 "4: ( { for ( int i@3 ; i@3 ; ++ i@3 ) { i@3 ++ ; } i@1 ++ ; } ) , i@1 ++ ) {\n"
                                 "5: i@1 ++ ;\n"
                                 "6: }\n"
                                 "7: }\n";
        ASSERT_EQUALS(expected1, tokenize(code1, false, "test.cpp"));
    }

    void varid59() { // #6696
        const char code[] = "class DLLSYM B;\n"
                            "struct B {\n"
                            "    ~B() {}\n"
                            "};";
        const char expected[] = "1: class DLLSYM B@1 ;\n" // In this line, we cannot really do better...
                                "2: struct B {\n"
                                "3: ~ B@1 ( ) { }\n" // ...but here we could
                                "4: } ;\n";
        const char wanted[] = "1: class DLLSYM B@1 ;\n"
                              "2: struct B {\n"
                              "3: ~ B ( ) { }\n"
                              "4: } ;\n";;
        TODO_ASSERT_EQUALS(wanted, expected, tokenize(code, false, "test.cpp"));
    }

    void varid60() { // #7267 - cast
        ASSERT_EQUALS("1: a = ( x y ) 10 ;\n",
                      tokenize("a=(x y)10;", false));
    }

    void varid61() {
        const char code[] = "void foo(int b) {\n"
                            "  void bar(int a, int b) {}\n"
                            "}";
        const char expected[] = "1: void foo ( int b@1 ) {\n"
                                "2: void bar ( int a@2 , int b@3 ) { }\n"
                                "3: }\n";
        ASSERT_EQUALS(expected, tokenize(code, false));
    }

    void varid62() {
        const char code[] = "void bar(int,int);\n"
                            "void f() {\n"
                            "    for (size_t c = 0; c < 42; ++c) {\n"
                            "        int x;\n"
                            "        bar(r, r * x);\n"
                            "    }\n"
                            "}";
        // Ensure that there is only one variable id for "x"
        ASSERT_EQUALS("same varid", compareVaridsForVariable(code, "x"));
    }

    void varid63() {
        const char code[] = "void f(boost::optional const& x) {}";
        const char expected[] = "1: void f ( boost :: optional < int > const & x@1 ) { }\n";
        ASSERT_EQUALS(expected, tokenize(code, false));
    }

    void varid_cpp_keywords_in_c_code() {
        const char code[] = "void f() {\n"
                            "    delete d;\n"
                            "    throw t;\n"
                            "}";

        const char expected[] = "1: void f ( ) {\n"
                                "2: delete d@1 ;\n"
                                "3: throw t@2 ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, tokenize(code,false,"test.c"));
    }

    void varid_cpp_keywords_in_c_code2() { // #5373
        const char code[] = "int clear_extent_bit(struct extent_io_tree *tree, u64 start, u64 end, "
                            "unsigned long bits, int wake, int delete, struct extent_state **cached_state, "
                            "gfp_t mask) {\n"
                            "  struct extent_state *state;\n"
                            "}"
                            "int clear_extent_dirty() {\n"
                            "  return clear_extent_bit(tree, start, end, EXTENT_DIRTY | EXTENT_DELALLOC | "
                            "                          EXTENT_DO_ACCOUNTING, 0, 0, NULL, mask);\n"
                            "}";
        tokenize(code, false, "test.c");
    }

    void varidFunctionCall1() {
        const char code[] ="void f() {\n"
                           "    int x;\n"
                           "    x = a(y*x,10);\n"
                           "}";
        const char expected[] = "1: void f ( ) {\n"
                                "2: int x@1 ;\n"
                                "3: x@1 = a ( y * x@1 , 10 ) ;\n"
                                "4: }\n";
        ASSERT_EQUALS(expected, tokenize(code, false, "test.c"));
    }

    void varidFunctionCall2() {
        // #2491
        const char code[] ="void f(int b) {\n"
                           "    x(a*b,10);\n"
                           "}";
        const std::string expected1("1: void f ( int b@1 ) {\n"
                                    "2: x ( a * b");
        const std::string expected2(" , 10 ) ;\n"
                                    "3: }\n");
        ASSERT_EQUALS(expected1+"@1"+expected2, tokenize(code,false,"test.c"));
    }

    void varidFunctionCall3() {
        // Ticket #2339
        const char code[] ="void f() {\n"
                           "    int a = 0;\n"
                           "    int b = c - (foo::bar * a);\n"
                           "}";

        const char expected[] = "1: void f ( ) {\n"
                                "2: int a@1 ; a@1 = 0 ;\n"
                                "3: int b@2 ; b@2 = c - ( foo :: bar * a@1 ) ;\n"
                                "4: }\n";

        ASSERT_EQUALS(expected, tokenize(code));
    }

    void varidFunctionCall4() {
        // Ticket #3280
        const char code1[] = "void f() { int x; fun(a,b*x); }";
        ASSERT_EQUALS("1: void f ( ) { int x@1 ; fun ( a , b * x@1 ) ; }\n",
                      tokenize(code1, false, "test.c"));
        const char code2[] = "void f(int a) { int x; fun(a,b*x); }";
        ASSERT_EQUALS("1: void f ( int a@1 ) { int x@2 ; fun ( a@1 , b * x@2 ) ; }\n",
                      tokenize(code2, false, "test.c"));
    }

    void varidFunctionCall5() {
        const char code[] = "void foo() { (f(x[2]))(x[2]); }";
        ASSERT_EQUALS("1: void foo ( ) { f ( x [ 2 ] ) ( x [ 2 ] ) ; }\n",
                      tokenize(code, false, "test.c"));
    }

    void varidStl() {
        const std::string actual = tokenize(
                                       "list ints;\n"
                                       "list::iterator it;\n"
                                       "std::vector dirs;\n"
                                       "std::map coords;\n"
                                       "std::tr1::unordered_map xy;\n"
                                       "std::list tokens;\n"
                                       "static std::vector ex1;\n"
                                       "extern std::vector ex2;\n"
                                       "std::map m;\n"
                                   );

        const char expected[] = "1: list < int > ints@1 ;\n"
                                "2: list < int > :: iterator it@2 ;\n"
                                "3: std :: vector < std :: string > dirs@3 ;\n"
                                "4: std :: map < int , int > coords@4 ;\n"
                                "5: std :: unordered_map < int , int > xy@5 ;\n"
                                "6: std :: list < boost :: wave :: token_id > tokens@6 ;\n"
                                "7: static std :: vector < CvsProcess * > ex1@7 ;\n"
                                "8: extern std :: vector < CvsProcess * > ex2@8 ;\n"
                                "9: std :: map < int , 1 > m@9 ;\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varidStl2() {
        const std::string actual = tokenize("std::bitset x;");

        const char expected[] = "1: std :: bitset < static_cast < int > ( 2 ) > x@1 ;\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varid_newauto() {
        ASSERT_EQUALS("1: void f ( ) { const new auto ( 0 ) ; }\n",
                      tokenize("void f(){new const auto(0);}"));
    }

    void varid_delete() {
        const std::string actual = tokenize(
                                       "void f()\n"
                                       "{\n"
                                       "  int *a;\n"
                                       "  delete a;\n"
                                       "}\n");

        const char expected[] = "1: void f ( )\n"
                                "2: {\n"
                                "3: int * a@1 ;\n"
                                "4: delete a@1 ;\n"
                                "5: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varid_functions() {
        {
            const std::string actual = tokenize(
                                           "void f();\n"
                                           "void f(){}\n", false, "test.c");

            const char expected[] = "1: void f ( ) ;\n"
                                    "2: void f ( ) { }\n";

            ASSERT_EQUALS(expected, actual);
        }

        {
            const std::string actual = tokenize(
                                           "A f(3);\n"
                                           "A f2(true);\n"
                                           "A g();\n"
                                           "A e(int c);\n", false, "test.c");

            const char expected[] = "1: A f@1 ( 3 ) ;\n"
                                    "2: A f2@2 ( true ) ;\n"
                                    "3: A g ( ) ;\n"
                                    "4: A e ( int c@3 ) ;\n";

            ASSERT_EQUALS(expected, actual);
        }

        {
            const std::string actual = tokenize(
                                           "void f1(int &p)\n"
                                           "{\n"
                                           "    p = 0;\n"
                                           "}\n"
                                           "void f2(std::string &str)\n"
                                           "{\n"
                                           "   str.clear();\n"
                                           "}\n"
                                           "void f3(const std::string &s)\n"
                                           "{\n"
                                           "    s.size();\n"
                                           "}\n");

            const char expected[] = "1: void f1 ( int & p@1 )\n"
                                    "2: {\n"
                                    "3: p@1 = 0 ;\n"
                                    "4: }\n"
                                    "5: void f2 ( std :: string & str@2 )\n"
                                    "6: {\n"
                                    "7: str@2 . clear ( ) ;\n"
                                    "8: }\n"
                                    "9: void f3 ( const std :: string & s@3 )\n"
                                    "10: {\n"
                                    "11: s@3 . size ( ) ;\n"
                                    "12: }\n";

            ASSERT_EQUALS(expected, actual);
        }

        {
            const std::string actual = tokenize("void f(struct foobar);", false, "test.c");
            const char expected[] = "1: void f ( struct foobar ) ;\n";
            ASSERT_EQUALS(expected, actual);
        }

        {
            const std::string actual = tokenize("bool f(X x, int=3);", false, "test.cpp");
            const char expected[] = "1: bool f ( X x@1 , int = 3 ) ;\n";
            ASSERT_EQUALS(expected, actual);
        }
    }

    void varid_sizeof() {
        const char code[] = "x = sizeof(a*b);";
        const char expected[] = "1: x = sizeof ( a * b ) ;\n";
        ASSERT_EQUALS(expected, tokenize(code,false,"test.c"));
    }

    void varid_reference_to_containers() {
        const std::string actual = tokenize(
                                       "void f()\n"
                                       "{\n"
                                       "    std::vector b;\n"
                                       "    std::vector &a = b;\n"
                                       "    std::vector *c = &b;\n"
                                       "}\n");

        const char expected[] = "1: void f ( )\n"
                                "2: {\n"
                                "3: std :: vector < int > b@1 ;\n"
                                "4: std :: vector < int > & a@2 = b@1 ;\n"
                                "5: std :: vector < int > * c@3 ; c@3 = & b@1 ;\n"
                                "6: }\n";

        ASSERT_EQUALS(expected, actual);
    }

    void varid_in_class1() {
        {
            const std::string actual = tokenize(
                                           "class Foo\n"
                                           "{\n"
                                           "public:\n"
                                           "    std::string name1;\n"
                                           "    std::string name2;\n"
                                           "};\n");

            const char expected[] = "1: class Foo\n"
                                    "2: {\n"
                                    "3: public:\n"
                                    "4: std :: string name1@1 ;\n"
                                    "5: std :: string name2@2 ;\n"
                                    "6: } ;\n";

            ASSERT_EQUALS(expected, actual);
        }

        {
            const std::string actual = tokenize(
                                           "class foo\n"
                                           "{\n"
                                           "public:\n"
                                           "    void do_something(const int x, const int y);\n"
                                           "    void bar();\n"
                                           "};\n"
                                           "\n"
                                           "void foo::bar()\n"
                                           "{\n"
                                           "    POINT pOutput = { 0 , 0 };\n"
                                           "    int x = pOutput.x;\n"
                                           "    int y = pOutput.y;\n"
                                           "}\n");

            const char expected[] = "1: class foo\n"
                                    "2: {\n"
                                    "3: public:\n"
                                    "4: void do_something ( const int x@1 , const int y@2 ) ;\n"
                                    "5: void bar ( ) ;\n"
                                    "6: } ;\n"
                                    "7:\n"
                                    "8: void foo :: bar ( )\n"
                                    "9: {\n"
                                    "10: POINT pOutput@3 ; pOutput@3 = { 0 , 0 } ;\n"
                                    "11: int x@4 ; x@4 = pOutput@3 . x@5 ;\n"
                                    "12: int y@6 ; y@6 = pOutput@3 . y@7 ;\n"
                                    "13: }\n";

            ASSERT_EQUALS(expected, actual);
        }
    }

    void varid_in_class2() {
        const std::string actual = tokenize(
                                       "struct Foo {\n"
                                       "    int x;\n"
                                       "};\n"
                                       "\n"
                                       "struct Bar {\n"
                                       "    Foo foo;\n"
                                       "    int x;\n"
                                       "    void f();\n"
                                       "};\n"
                                       "\n"
                                       "void Bar::f()\n"
                                       "{\n"
                                       "    foo.x = x;\n"
                                       "}\n");
        const char expected[] = "1: struct Foo {\n"
                                "2: int x@1 ;\n"
                                "3: } ;\n"
                                "4:\n"
                                "5: struct Bar {\n"
                                "6: Foo foo@2 ;\n"
                                "7: int x@3 ;\n"
                                "8: void f ( ) ;\n"
                                "9: } ;\n"
                                "10:\n"
                                "11: void Bar :: f ( )\n"
                                "12: {\n"
                                "13: foo@2 . x@4 = x@3 ;\n"
                                "14: }\n";
        ASSERT_EQUALS(expected, actual);
    }

    void varid_in_class3() {
        const char code[] = "class Foo {\n"
                            "    void blah() {\n"
                            "        Bar x(*this);\n"  // 

Web Proxy Viewer  |  New URL  |  Original Page