Использование fwrite () и fread () с malloc и realloc - PullRequest
0 голосов
/ 19 февраля 2012

У меня проблемы с моим проектом для класса. Я сразу скажу, что Я не прошу, чтобы это было сделано для меня , я просто хочу больше разъяснений о том, как использовать эти функции. Похоже, что я использую их правильно, потому что он будет работать до добавления 16 элементов, но затем зависнет на fclose () или segfaults.

Вот с чем я работаю. Это файловая система FAT16:

directoryTable - это «массив» структур.

void writeDirectory(int FATTable[], directoryEntry* directoryTable)
{   
    int currentCluster = 1;
    directoryEntry* currentWrite = directoryTable;

    FILE* theFile = fopen (fileSystemName, "rb+"); 
    if(theFile != NULL)
    {
        cout << fseek (theFile, (clusterSize * currentCluster), SEEK_SET) << endl;
        cout << fwrite(currentWrite, clusterSize, 1, theFile) << endl ;

        while(FATTable[currentCluster] != 0xFFFF)
        {
            currentWrite = currentWrite + numberOfEntries;
            currentCluster = FATTable[currentCluster];
            cout << fseek (theFile, (clusterSize * currentCluster), SEEK_SET) << endl;
            cout << fwrite(currentWrite, clusterSize, 1, theFile) << endl; 
        }

        fflush(theFile);
        cout << "Closing.." << errno << endl;
        fclose(theFile);
    }
    else
        cout << "FILE COULDN'T OPEN." << endl; 

    //Clean up that pointer
    free(directoryTable);
}

По сути, указатель (currentWrite) начинается с начала другого указателя (directoryTable) и записывает размер кластера байтов по одному в части файла. Если осталось больше массива / указателя (directoryTable), он будет увеличивать currentWrite до clusterSize байтов и записывать снова.

Затем он будет читать и строить массив / указатель, используя это:

directoryEntry* readDirectory(int FATTable[])
{   
    int currentCluster = directoryIndex; 

    //Allocate a clusterSize of memory
    directoryEntry* directoryTable;
    directoryTable = (directoryEntry*) malloc(clusterSize);

    if(directoryTable == NULL)
        cout << "!!! ERROR: Not enough memory!" << endl;

    //A pointer to a part of that array
    directoryEntry* currentRead = directoryTable;
    numberOfDirTables = 1;

    FILE* theFile = fopen (fileSystemName, "rb+"); 
    if(theFile != NULL)
    {
        //Seek to a particular cluster in the file (
        cout << fseek (theFile, (clusterSize * currentCluster), SEEK_SET) << endl;
        cout << fread(currentRead, clusterSize, 1, theFile) << endl;

        while(FATTable[currentCluster] != 0xFFFF)
        {
            numberOfDirTables++; 
            currentCluster = FATTable[currentCluster];
            directoryTable = (directoryEntry*) realloc(directoryTable, (clusterSize*numberOfDirTables));
            if(directoryTable == NULL)
                cout << "!!! ERROR: Not enough memory!" << endl;
            currentRead = currentRead + numberOfEntries;
            cout << fseek (theFile, (clusterSize * currentCluster), SEEK_SET) << endl;

            cout << fread(currentRead, clusterSize, 1, theFile) << endl;
        }
        cout << "Closing..." << errno << endl;
        fclose(theFile);
        cout << "Closed." << endl;
    }
    else
        cout << "FILE COULDN'T OPEN." << endl; 
    return directoryTable;
}

По сути, он будет считывать данные из первого кластера и помещать их в массив. Затем он будет увеличивать currentRead clusterSize на количество байтов и читать из другого кластера. Но он перераспределяется первым, поэтому массив расширяется еще одним байтом clusterSize.

Итак, мой вопрос: правильно ли я использую fwrite, fread, malloc и realloc? Казалось бы, так как он работает до определенного момента. Но я не слишком силен в C ++, поэтому мне кажется, что я упускаю небольшую вещь, которая вызывает серьезную проблему с памятью.

Кроме того, я должен использовать вместо этого calloc, так как я строю массив структур?

1 Ответ

1 голос
/ 19 февраля 2012

Когда вы используете realloc () directoryTable, он (вероятно) получает другое пространство памяти (адрес), чем раньше.Итак, после realloc, куда указывает currentRead?(Ведущий вопрос ..)

...