私は約1000枚の画像を読み取り、その内容の統計要約を作成するプログラムを持っています。各イメージはOpenMPを使用して独自のスレッドで処理され、プロセッサの数に合わせてスレッド制限を設定しています。
約2週間前まで、プログラムは正常に実行されていました。ただし、プログラムを複数回実行すると、システムの速度が低下し、最終的にフリーズします。
トラブルシューティングを行うために、プログラムが実行していることをエミュレートする以下の簡単なコードを作成しました。このコードは、35行目で数個のファイルのみを読み取ろうとした後、元のプログラムと同じようにシステムをフリーズします。
プログラムを実行し、失敗するたびに以前のカーネルに続けて戻しましたが、バージョン3.6.8までのすべての3.6カーネルで失敗することがわかりました。
ただし、カーネル3.5.6に戻ると、動作します。
test.cc:
1 #include <cstdio>
2 #include <iostream>
3 #include <vector>
4 #include <unistd.h>
5
6 using namespace std;
7
8 int main ()
9 {
10 // number of files
11 const size_t N = 1000;
12 // total system memory
13 const size_t MEM = sysconf (_SC_PHYS_PAGES) * sysconf (_SC_PAGE_SIZE);
14 // file size
15 const size_t SZ = MEM/N;
16
17 // create temp filenames
18 vector<string> fn (N);
19 for (size_t i = 0; i < fn.size (); ++i)
20 fn[i] = string (tmpnam (NULL));
21
22 // write a bunch of files to disk
23 for (size_t i = 0; i < fn.size (); ++i)
24 {
25 vector<char> a (SZ);
26 FILE *fp = fopen (fn[i].c_str (), "wb");
27 fwrite (&a[0], a.size (), 1, fp);
28 clog << fn[i] << " written" << endl;
29 }
30
31 // read a bunch of files from disk
32 #pragma omp parallel for
33 for (size_t i = 0; i < fn.size (); ++i)
34 {
35 vector<char> a (SZ);
36 FILE *fp = fopen (fn[i].c_str (), "rb");
37 fread (&a[0], a.size (), 1, fp);
38 clog << fn[i] << " read" << endl;
39 }
40
41 return 0;
42 }
Makefile:
1 a:$
2 g++ -fopenmp -Wall -o test -g test.cc$
3 ./test$
私の質問は、このプログラムが失敗する原因となるが、バージョン3.5では失敗しないカーネル3.6の違いは何ですか?