FOPEN問題 - 開いたファイルが多すぎます
-
02-10-2019 - |
質問
Win XPで実行されているマルチスレッドアプリケーションがあります。特定の段階では、スレッドの1つが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が失敗する理由は何ですか?
編集:
簡単なシングルスレッドテストアプリケーションを書きました。このアプリは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);
}
}
}
解決
Win32では、すべてのCRT関数が最終的に下のWin32 APIを使用してエンドアップすると思います。したがって、この場合、おそらくwin32のcreatefile/openfileを使用する必要があります。現在、CreatFile/OpenFile APIは、ファイル(ファイル、ディレクトリ、通信ポート、パイプ、メールスロット、ドライブボリュームなど)のみを対象としていません。したがって、これらのリソースの数に応じて実際のアプリケーションでは、最大オープンファイルが異なる場合があります。アプリケーションについてあまり説明していないので。これが私の最初の推測です。時間許可がこれを通過した場合 http://blogs.technet.com/b/markrussinovich/archive/2009/09/29/3283844.aspx
他のヒント
これはあなたのオペレーティングシステムの制限だと思います。それは多くのことに依存することがあります:ファイル記述子の表現方法、消費するメモリなど。
そして、私はあなたがそれについてできることはあまりないと思います。おそらく、その制限を微調整するパラメーターがいくつかあります。
本当の問題は、それほど多くのファイルを同時に開く必要があるということです。つまり、100以上の異なるファイルを読み取ろうとしている100以上のスレッドがある場合でも、おそらくそれらを同時に読むことができないでしょう。たとえば、例として50スレッドを持つことよりも良い結果は得られないでしょう。
あなたが何を達成しようとしているのかわからないので、より正確にすることは困難です。