Linux System V IPC 共有メモリ セグメントがあり、1 つのプロセスによって読み込まれ、他の多くのプロセスによって読み取られます。すべてのプロセスは、コンストラクタ/デストラクタ メソッドの一部としてセグメントのルックアップ、アタッチ、およびデタッチを処理するクラスの形式で、共有メモリ セグメントへのインターフェイスを使用します。
ここでの問題は、セグメントが「分割」されていることがときどき見られることです。ここで言いたいのは、「ipcs -m -s」の出力を見ると、2 つのセグメントがリストされていることがわかるということです。セグメントにアタッチするためのすべての新しい試みを取得します。ただし、カーネルにセグメントの破棄を実際に要求しているわけではありません。ここで何が起こっているのですか?!
注意すべきもう 1 つのことは、残念ながら、これが実行されているシステムは、メモリ部門で深刻にオーバーコミットされていることです。1 GB の物理メモリがあり、スワップはなく、/proc/meminfo の Committed_AS は約 2.5 GB のコミット済みメモリを報告しています。幸いなことに、システム プロセスは実際にはこれほど多くのメモリを使用していません...単に要求しているだけです (vmstat で報告されているように、まだ約 660MB の「空き」メモリがあります)。これが理想からかけ離れていることは承知していますが、当面の間、オーバーコミットされたメモリについて私にできることは何もありません。ただし、kernel/libc ソースを参照すると、ユーザーの要求以外の理由で共有メモリ セグメントを削除するようにマークするものは何も表示されません (ただし、どこかに隠されているのを見逃した可能性があります)。
参考までに、共有メモリ インターフェイス クラスのコンストラクタを次に示します。
const char* shm_ftok_pathname = "/usr/bin";
int shm_ftok_proj_id = 21;
// creates a key from a file path so different processes will get same key
key_t m_shm_key = ftok(shm_ftok_pathname, shm_ftok_proj_id);
if ( m_shm_key == -1 )
{
fprintf(stderr,"Couldn't get the key for the shared memory\n%s\n",strerror(errno));
exit ( status );
}
m_shm_id = shmget(m_shm_key, sizeof(shm_data_s), (IPC_CREAT | 0666));
if (m_shm_id < 0)
{
fprintf(stderr,"Couldn't get the shared memory ID\nerrno = %s \n",strerror(errno));
exit ( status );
}
// get a ptr to shared memory, which is a shared mem struct
// second arg of 0 says let OS choose shm address
m_shm_data_ptr = (shm_data_s *)shmat(m_shm_id, 0, 0);
if ( (int)m_shm_data_ptr == -1 )
{
fprintf(stderr,"Couldn't get the shared memory pointer\n");
exit ( status );
}
Linux 2.6.18-5-686 #1 SMP Fri Jun 1 00:47:00 UTC 2007 i686 GNU/Linux