如何修复g ++内存范围重叠?

时间:2014-11-22 07:48:56

标签: c++ linux memory g++ range

我开发了一个在Visual Studio中完美运行的C ++程序,它接受一个int数组,两个C字符串数组和一个大C字符串,并尝试查找大C字符串是否包含其中的任何其他C字符串相距一定的距离。

编辑:由于这是一项学校作业,我限制使用C字符串而不是std :: string和strcopy而不是memmove。

当我在g ++上运行程序时,收到以下错误消息:

==17764==ERROR: AddressSanitizer: strcpy-param-overlap: memory ranges [0x7fff7213d993,0x7fff7213d994) and [0x7fff7213d993, 0x7fff7213d994) overlap
    #0 0x7fa2141eec11 in __interceptor_strcpy ../../../../gcc-4.9.2/libsanitizer/asan/asan_interceptors.cc:486
    #1 0x402b2a in standardizeRules(int*, char (*) [21], char (*) [21], int) (/w/home.02/cs/ugrad/justinn/match+0x402b2a)
    #2 0x40176d in main (/w/home.02/cs/ugrad/justinn/match+0x40176d)
    #3 0x376f01ed1c in __libc_start_main (/lib64/libc.so.6+0x376f01ed1c)
    #4 0x4011f8 (/w/home.02/cs/ugrad/justinn/match+0x4011f8)

Address 0x7fff7213d993 is located in stack of thread T0 at offset 787 in frame
    #0 0x401347 in main (/w/home.02/cs/ugrad/justinn/match+0x401347)

  This frame has 7 object(s):
    [32, 48) 'test1dist'
    [96, 144) 'distance'
    [192, 276) 'test1w1'
    [320, 404) 'test1w2'
    [448, 577) 'doc'
    [640, 892) 'word1' <== Memory access at offset 787 is inside this variable
    [928, 1180) 'word2'
HINT: this may be a false positive if your program uses some custom stack unwind mechanism or swapcontext
      (longjmp and C++ exceptions *are* supported)
Address 0x7fff7213d993 is located in stack of thread T0 at offset 787 in frame
    #0 0x401347 in main (/w/home.02/cs/ugrad/justinn/match+0x401347)

  This frame has 7 object(s):
    [32, 48) 'test1dist'
    [96, 144) 'distance'
    [192, 276) 'test1w1'
    [320, 404) 'test1w2'
    [448, 577) 'doc'
    [640, 892) 'word1' <== Memory access at offset 787 is inside this variable
    [928, 1180) 'word2'
HINT: this may be a false positive if your program uses some custom stack unwind mechanism or swapcontext
      (longjmp and C++ exceptions *are* supported)
SUMMARY: AddressSanitizer: strcpy-param-overlap ../../../../gcc-4.9.2/libsanitizer/asan/asan_interceptors.cc:486 __interceptor_strcpy
==17764==ABORTING

导致此错误的原因是什么?如何解决?

谢谢!

编辑: 这是代码:

int standardizeRules(int distance[], char word1[][MAX_WORD_LENGTH + 1], char word2[][MAX_WORD_LENGTH + 1], int nRules)
{
    int validCheck = nRules; //validCheck holds the number of actual valid rules to avoid checking known bad rules
    for (int a = 0; a < validCheck; a++) //converts every letter in every string to lowercase
    {
        for (int b = 0; b < MAX_WORD_LENGTH; b++)
        {
            word1[a][b] = tolower(word1[a][b]);
            word2[a][b] = tolower(word2[a][b]);
        }
    }
    for (int count = 0; count < validCheck; count++) //repeat rule testing, if a repeat is found it sets distance to 0 so code automatically filters it out
    {
        for (int x = count + 1; x < validCheck; x++) //compares current string to all other strings behind it in both arrays
        {
            bool repeat = false;
            //cerr << "Testing: " << x << endl;
            if (strcmp(word1[count], word1[x]) == 0)
            {
                if (strcmp(word2[count], word2[x]) == 0)
                {
                    //cerr << "Repeat rule" << endl;
                    repeat = true;
                }
            }
            else if (strcmp(word1[count], word2[x]) == 0)
            {
                if (strcmp(word2[count], word1[x]) == 0)
                {
                    //cerr << "Repeat rule" << endl;
                    repeat = true;
                }
            }
            else if (strcmp(word2[count], word1[x]) == 0)
            {
                if (strcmp(word1[count], word2[x]) == 0)
                {
                    //cerr << "Repeat rule" << endl;
                    repeat = true;
                }
            }
            else if (strcmp(word2[count], word2[x]) == 0)
            {
                if (strcmp(word1[count], word1[x]) == 0)
                {
                    //cerr << "Repeat rule" << endl;
                    repeat = true;
                }
            }
            if (repeat) //tests to see which distance is lesser, then sets that to 0
            {
                //cerr << "Repeat testing" << endl;
                if (distance[count] < distance[x])
                {
                    distance[count] = 0;
                }
                else
                {
                    distance[x] = 0;
                }
            }
            //cerr << "X:" << x << endl;
        }
        //cerr << "Done with repeat" << endl;
        bool replace = false;
        if (distance[count] < 1) //non-positive distance check
        {
            //cerr << "Bad distance: " << distance[count] << endl;
            replace = true;
        }
        if (strlen(word1[count]) == 0 || strlen(word2[count]) == 0) //empty string check
        {
            //cerr << "Empty string" << endl;
            replace = true;
        }
        for (int charPos = 0; charPos < MAX_WORD_LENGTH; charPos++) //non-alphabetical check
        {
            if (word1[count][charPos] != '\0' && word2[count][charPos] != '\0')
            {
                if (!(isalpha(word1[count][charPos]) && isalpha(word2[count][charPos])))
                {
                    //cerr << "Bad character 1: " << word1[count][charPos] << ", Bad character 2: " << word2[count][charPos] << endl;
                    replace = true;
                }
            }
        }
        if (replace) //if bad rule, swaps current rule with last valid (or unchecked) rule
        {
            //cerr << "Begin" << endl;
            for (int x = 0; x < validCheck; x++)
            {
                //cerr << "Dist: " << distance[x] << ", word1: " << word1[x] << ", word2: " << word2[x] << endl;
            }
            //cerr << endl;
            int distReplace = distance[validCheck - 1];
            distance[validCheck - 1] = distance[count];
            distance[count] = distReplace;
            char word1Rep[MAX_WORD_LENGTH + 1];
            char word2Rep[MAX_WORD_LENGTH + 1];
            strcpy(word1Rep, word1[validCheck - 1]);
            strcpy(word2Rep, word2[validCheck - 1]);
            strcpy(word1[validCheck - 1], word1[count]);
            strcpy(word2[validCheck - 1], word2[count]);
            strcpy(word1[count], word1Rep);
            strcpy(word2[count], word2Rep);
            for (int x = 0; x < validCheck; x++)
            {
                //cerr << "Dist: " << distance[x] << ", word1: " << word1[x] << ", word2: " << word2[x] << endl;
            }
            validCheck--;
            count--;
            //cerr << "End" << endl;
        }
    }
    for (int x = 0; x < validCheck; x++)
    {
        //cerr << "Dist: " << distance[x] << ", word1: " << word1[x] << ", word2: " << word2[x] << endl;
    }
    //cerr << "validCheck: " << validCheck << endl;
    return validCheck;
}

int determineQuality(const int distance[], const char word1[][MAX_WORD_LENGTH + 1], const char word2[][MAX_WORD_LENGTH + 1], int nRules, const char document[])
{
    //cerr << "Checkpoint A" << endl;
    int quality = 0; //counter for matches
    char words[200][200]; //array to hold all words in document
    int count = 0;
    int arrayPos = 0;
    while (count < strlen(document)) //loop through document
    {
        //cerr << "Checkpoint B" << endl;
        int charPos = 0;
        while (count < strlen(document) && document[count] != ' ') //split document up into words and record words in array
        {
            //cerr << "Checkpoint C: " << count << endl;
            if (isalpha(document[count]) && charPos < 200) //record only alphabetical characters
            {
                words[arrayPos][charPos] = tolower(document[count]);
                charPos++;
            }
            count++;
        }
        count++;
        words[arrayPos][charPos] = '\0'; //end each word with a null byte
        //cerr << "Word: " << words[arrayPos] << endl;
        arrayPos++;
    }
    for (int ruleCount = 0; ruleCount < nRules; ruleCount++) //compare rules to words
    {
        bool match = false; //boolean to record if rule has a match or not
        for (int wordCount = 0; wordCount <= arrayPos; wordCount++)
        {
            if (strcmp(word1[ruleCount], words[wordCount]) == 0) //if word1 finds a match, look for a match for word2 within distance
            {
                int beginning = wordCount - distance[ruleCount];
                if (beginning < 0)
                {
                    beginning = 0;
                }
                int end = wordCount + distance[ruleCount];
                if (end >= arrayPos)
                {
                    end = arrayPos;
                }
                for (int arrayCheck = beginning; arrayCheck <= end; arrayCheck++)
                {
                    if (strcmp(word2[ruleCount], words[arrayCheck]) == 0)
                    {
                        match = true;
                    }
                }
            }
            if (strcmp(word2[ruleCount], words[wordCount]) == 0) //if word2 find a match, look for a match for word1 within distance
            {
                int beginning = wordCount - distance[ruleCount];
                if (beginning < 0)
                {
                    beginning = 0;
                }
                int end = wordCount + distance[ruleCount];
                if (end >= arrayPos)
                {
                    end = arrayPos;
                }
                for (int arrayCheck = beginning; arrayCheck <= end; arrayCheck++)
                {
                    if (strcmp(word1[ruleCount], words[arrayCheck]) == 0)
                    {
                        match = true;
                    }
                }
            }
        }
        if (match) //if rule had a match, increment quality
        {
            quality++;
        }
    }
    return quality;
}

1 个答案:

答案 0 :(得分:0)

感谢您的帮助。

经过进一步调查后,我发现错误是因为strcpy()使用与源相同的目的地。