проблема с fopen - слишком много открытых файлов - PullRequest
4 голосов
/ 06 июля 2010

У меня многопоточное приложение, работающее на Win XP. На определенном этапе одному из потоков не удается открыть существующий файл с помощью функции fopen. Функция _get_errno возвращает EMFILE, что означает Слишком много открытых файлов. Нет доступных файловых дескрипторов . FOPEN_MAX для моей платформы - 20. _getmaxstdio возвращает 512. Я проверил это с помощью WinDbg, и я вижу, что открыто около 100 файлов:

788 Handles
Type            Count
Event           201
Section         12
File            101
Port            3
Directory       3
Mutant          32
WindowStation   2
Semaphore       351
Key             12
Thread          63
Desktop         1
IoCompletion    6
KeyedEvent      1

В чем причина отказа fopen?


EDIT:

Я написал простое однопоточное тестовое приложение. Это приложение может открыть 510 файлов. Я не понимаю, почему это приложение может открывать больше файлов, чем многопоточное приложение. Это может быть из-за утечки дескриптора файла?

#include <cstdio> 
#include <cassert> 
#include <cerrno> 
void main() 
{ 
    int counter(0); 

    while (true) 
    { 
        char buffer[256] = {0}; 
        sprintf(buffer, "C:\\temp\\abc\\abc%d.txt", counter++); 
        FILE* hFile = fopen(buffer, "wb+"); 
        if (0 == hFile) 
        { 
            // check error code 
            int err(0); 
            errno_t ret = _get_errno(&err); 
            assert(0 == ret); 
            int maxAllowed = _getmaxstdio(); 
            assert(hFile); 
        } 
    } 
}

Ответы [ 2 ]

5 голосов
/ 06 июля 2010

Полагаю, это ограничение вашей операционной системы.Это может зависеть от многих вещей: способ представления файловых дескрипторов, используемая ими память и т. Д.

И я полагаю, что вы ничего не можете с этим поделать.Возможно, есть какой-то параметр для настройки этого ограничения.

Реальный вопрос в том, нужно ли вам открывать столько файлов одновременно?Я имею в виду, что даже если у вас есть более 100 потоков, пытающихся прочитать более 100 различных файлов, они, вероятно, не смогут читать их одновременно, и вы, вероятно, не получите лучшего результата, чем, например, 50 потоков.

Трудно быть более точным, поскольку мы не знаем, чего вы пытаетесь достичь.

2 голосов
/ 08 июля 2010

Я думаю, что в win32 все функции crt в конечном итоге завершатся использованием API-интерфейса win32. Так что в этом случае, скорее всего, он должен использовать CreateFile / OpenFile из win32. Теперь API CreatFile / OpenFile предназначен не только для файлов (файлы, каталоги, коммуникационные порты, каналы, почтовые слоты, тома дисков и т. Д.,). Так что в реальном приложении в зависимости от количества этих ресурсов ваш максимально открытый файл может отличаться. Так как вы не очень много рассказали о приложении. Это мое первое предположение. Если позволяет время, пройдите это http://blogs.technet.com/b/markrussinovich/archive/2009/09/29/3283844.aspx

...