У меня есть программа, которая получает поток необработанных данных с разных камер и записывает их на диск. Программа запускает такие записи в течение ~ 2 минут, а затем для обработки кадров используется другая программа.Написание многих больших файлов быстро в C++
Каждый необработанный кадр составляет 2 МБ, а частота кадров составляет 30 кадров в секунду (то есть скорость передачи данных составляет около 60 МБ/с), и я пишу на SSD, который может легко обрабатывать поддерживаемый> 150 МБ/с (проверен путем копирования 4000 2 МБ файлы с другого диска, которые заняли 38 секунд, и Process Explorer показывает постоянную активность IO).
Моя проблема заключается в том, что иногда звонит fopen()
, fwrite()
и fclose()
киоск на срок до 5 секунд, что означает, что 300MB кадров создать в памяти, как бревно назад, и после того, как некоторые из этих задержек я ударил предел 4 Гб 32-битный процесс. (Когда задержка происходит, Process Explorer показывает разрыв в активности IO)
Существует поток, который запускает цикл вызова этой функции для каждого нового кадра, который добавляется в очередь:
writeFrame(char* data, size_t dataSize, char* filepath)
{
// Time block 2
FILE* pFile = NULL;
fopen(&pFile, filepath, "wb");
// End Time block 2
// Time block 3
fwrite(data,1,dataSize,pFile);
// End Time block 3
// Time block 4
fclose(pFile);
// End Time block 4
}
(Там в ошибка проверки тоже в фактическом коде, но это не имеет никакого отношения к этой проблеме) Я регистрирую время, которое требуется для каждого из блоков, и общее время, необходимое для запуска функции, и я получаю результаты, которые в большинстве случаев выглядят например: (раз в мс)
TotalT,5, FOpenT,1, FWriteT,2, FCloseT,2
TotalT,4, FOpenT,1, FWriteT,1, FCloseT,2
TotalT,5, FOpenT,1, FWriteT,2, FCloseT,2
т.е. ~ 5 мс для запуска целых функций, ~ 1 мс для открытия файла, ~ 2 мс для вызова записи и ~ 2 мс для закрытия файла.
Однако иногда (в среднем около 1 на каждые 50 кадров, но иногда это может быть тысячи кадров между этой проблемой происходящего), я получаю кадры, которые принимают более 4000ms:
TotalT,4032, FOpenT,4023, FWriteT,6, FCloseT,3
и
TotalT,1533, FOpenT,1, FWriteT,2, FCloseT,1530
Все кадры имеют одинаковый размер, и его никогда не fwrite
что берет дополнительное время, всегда fopen
или fclose
Никакой другой процесс не читает/не записывает/не записывает этот SSD (подтвержденный с помощью Process Monitor).
Кто-нибудь знает, что может быть причиной этой проблемы и/или любым способом избежать/смягчить эту проблему?
Каждый кадр записывается в отдельный файл? Возможно, вы могли бы записывать группы кадров в один файл и иметь отдельный поток, который обрабатывает их, чтобы впоследствии взять файл из N кадров и сегментировать их в отдельные файлы (чтобы облегчить вызовы fopen/fclose в потоке обработки видео). Тогда это позволит вашей функции writeFrame работать намного быстрее и не замедлять процесс захвата видео. – spartygw
рассмотрите проверку того, что 'fopen' и' fclose' действительно успешно открываются и закрываются, также проверяют, сколько потоков запущено, возможно, вы нажимаете максимальную величину потока. –
Вы не упомянули о платформе или типе файловой системы, используемом на ssd. Если это окна, это будет хорошее место для использования асинхронных записей. – Dan