• ベストアンサー

共有メモリについて

Linux関連でプログラムの作成をしているのですが、 共有メモリについての知識がほとんどありません。 それで 1.共有メモリの最大サイズ(カーネルの設定によると思いますが、デフォルトの値など) 2.共有メモリを使用するさいの排他処理について などがわかる方、もしくは解説したHPなどがありましたらどうか教えてください。 よろしくお願いします。

質問者が選んだベストアンサー

  • ベストアンサー
  • Fooky
  • ベストアンサー率71% (59/82)
回答No.2

プログラミングのセクションで尋ねればもっと 早く回答が得られたと思いますよ。 1.について。  SHMMAX:1セグメント(1回のshmgetで割り当てられる  共有メモリ領域)あたりの最大バイト数  SHMALL:システム全体の共有メモリの最大ページ数  1.1 /proc/sys/kernel/shmmax, /proc/sys/kernel/shmall     をcatで見れば、現在のshmmaxとshmallの値が分かると思います。  1.2 man shmgetに書いてないでしょうか?  1.3 カーネルソースをインストールしていれば、ソースを見てみると      どこかに書いてあると思います。      /usr/src/linux/include/asm-i386/page.h      /usr/src/linux/include/asm-i386/shmparam.h      などがそうじゃないかと思います。  ページサイズは.../page.hの中で、1UL << 12となっています。  1を12回左シフトすると読めば、4096バイトでしょうか? 2.SysV IPCには排他制御の仕組みとしてセマフォを実現する関数群 (semget, semctl, semop)が用意されていますが、どうせ共有メモリ を使用するなら、自分でセマフォのようなものを作られたら良いと 思います。  例えば、共有メモリの先頭にchar型1文字分の領域を確保しておいて、 共有メモリへの読み書きの前には必ずそこをチェックし、0ならば それを1に変更してから読み書きをする。読み書きが終われば0に戻す。 チェック時に1ならば0になるまで待つ。というようにすれば簡単な 排他制御ができます。データは共有メモリの先頭からchar1個分だけ ずれたところから格納するようにします。  工夫次第で色んな形の排他制御ができます。例えば、上記のcharを 読み出し用と書き込み用を用意すると、読み出しは重複して行って も良いが、書き込みはダメ、というような排他制御が行えます。 (ただしその際は上記のチェックアルゴリズムでは不十分で、  ひと工夫必要です。)  また、共有メモリ領域を複数の部分に分けてそれぞれについて 排他制御を行うと、一々共有メモリ全体がロックされることがないので、 共有メモリへのアクセスが頻繁に行われるようなら、効率があがる と思います。  あるいは、排他制御用のcharフラッグとデータ領域を一まとめにした 構造体やクラスを宣言して、メモリ領域のポインタを構造体ポインタに キャストして、構造体やクラスのメンバ関数を通してのみ共有メモリに アクセスするようにすると、排他制御機構を構造体やクラスのなかに 隠すことができ、プログラムがすっきりすると思います。

clow_h
質問者

お礼

詳しい解説、ありがとうございました。 とても参考になりました。

その他の回答 (1)

回答No.1

turbolinuxで良ければ参考URLを見てみて下さい。 他のlinuxも同様かと思います。 ※共有メモリ等はいろいろなプログラムで既に使用されている場合があるのでipcs等で使用状況を把握してからID 等を割り振ったほうが良いと思います。

参考URL:
http://www.turbolinux.co.jp/world/library/features/c_magazine/vol_05.html
clow_h
質問者

お礼

ありがとうございます。 参考URL、とっても勉強になりました。

関連するQ&A

  • 仮想メモリの設定

    [Win2000,メモリ384MB] なんかよくわからず仮想メモリのサイズをいじってしまったので、デフォルトの状態に 戻したいのですがデフォルトのサイズを忘れてしまいました。 初期サイズと最大サイズというのがありますが、それぞれ設定の仕方を教えて下さい。 また、推奨サイズあるのですが、この推奨というのは初期・最大どちらを指しているのでしょう? よろしくおねがいします。

  • 64bit Linux上で32bitアプリケーションを使って共有メモリアクセス

    64bit Linux と共有メモリとの関係についてどなたか教えて いただけないでしょうか。  (現段階では、マシンもOSも64bitのものは無く、導入前での   検討段階です) 使いたいと思っているのは Red Hat Enterprise Linux 3.0 です。 現在動かしているアプリケーションが使っている共有メモリの サイズが大きくなってきたために64bitのLinuxを検討しています。 ただし、プログラム移行の手間を最小限にするめ、64bit環境上で 32bitライブラリにリンクしてmakeし直す程度の対応で済ませたいと 思っています(言語はCです)。 このような32bitアプリケーションが発行する共有メモリ関係の API‥たとえば、shmget()とかshmat()‥の呼び出しは、どこかの レイヤで最終的に64bit化されて動くと想像しています。 そうすると、32bit用のインターフェースに破綻を来たさない限りは、 総量で4GB超の共有メモリをアクセス可能(具体的には、総量として 4GBを越えて取得でき、参照時にはマッピングサイズが小さければ、 それらのいずれの部分もマッピングできる)と想像しているのですが そのような理解で良いでしょうか。 ちなみに、4GB超の大きなメモリを1つ使うわけではなく、100個前後 に分散した取得/マッピングをしています。つまり個々のブロックは 小さなサイズです。 よろしくお願いします。

  • 共有メモリを拡大するがゆえの弊害ってありますか?

    共有メモリを拡大するがゆえの弊害ってありますか? Oracleの設定で共有メモリを1週間前に大きくしました。 大きくした理由はそんなようなエラーメッセージが出たからだけです。 そもそも共有メモリというものに対して知識がそんなにないのにやったのがいけないのかもしれませんがなんだかパフォーマンスが悪くなった気がします。(直感だけですが・・・) 実際どんなんでしょうか?あとバッファキャッシュってなんですか? ご解説いただけるとうれしいです。

  • Linuxがサポートする最大メモリ

    Linuxがサポートする最大メモリですが、何となく4GBだと思ってきました(何かで見たので・・というレベル)。今回とあるサーバにメモリを追加したいのですが、一体どこまで拡張できるのかがわからないのです。 対象のサーバは以下の通りです。 Kernel: Linux hogehoge 2.4.9-e.25smp #1 SMP Fri Jun 6 18:11:40 EDT 2003 i686 unknown OS: Red Hat Linux Advanced Server release 2.1AS (Pensacola) Redhatのサイトを見るとASなら16GBまでメモリを確保できるとあるのですが、稼働中のサーバはバージョン2.1なのでそのままそれが適用できるのかがわかりません(現行製品は3.0) このパッケージ(RHEL2.1AS)、カーネルで利用できるメモリの最大値は何GBなのでしょうか? 最大メモリが何に依存するのかについての情報も頂ければ幸いです(ここを読め!など・・・)

  • 複数の共有メモリの作成

    同じPC内に複数の共有メモリを作ろうとしています。自分の考えでは共有メモリを作成するときに shmget(key_t key, int size, int shmflg) のkeyを変えれば複数の共有メモリを作れると思ったのですがうまくいきません。ちなみにkeyは key = ftok(const char *pathname, int proj_id); で取得していて、pathnameとproj_idを変えればkey_tの値も変わり、複数の共有メモリが確保できると思ったのですが・・・。 また、ipcsで確認したところできた共有メモリのキーが0xffffffffになっているのも気になりました。普通は0x00000000になるべきなんでしょうか?

  • C/Sでのメモリの共有

    クライアントからの指示でそれに応じてサーバの処理を行わせようとしたいのですが、以前はファイル書き込みでやろうとしていました。が、速度の問題等があるらしくて、メモリを参照するほうがよいのではということで考えております。 まだ初心者なもので、知識がありません。クライアントとサーバ間でメモリの共有をする一般的な方法を教えていただきたいのですが。よろしくお願いいたします。

  • DLLの共有メモリと排他処理???

    共有メモリを持つDLLを作りました 機能は単純です (1)カウンターをアップしてその値を返す ⇒ CountUp() (2)カウンターの現在値を返す ⇒ TotalCount() #pragma data_seg(".HShared") static int m = 0; #pragma data_seg() #pragma comment(linker,"/Section:.HShared,rws") int WINAPI DllMain(HINSTANCE hInst, DWORD fdwReason, PVOID pvReserved) { return TRUE; } EXPORT int CALLBACK CountUP() { m++; return m; } EXPORT int CALLBACK TotalCount() { return m; } このDLLは多数のアプリから呼ばれます 当然同時に呼ばれることもあるでしょう カウンター m には排他処理を施してありません 大丈夫でしょうか? それとも排他は Windows様 がしてくれているのでしょうか? 色々と調べてみましたが良く分かりません 宜しくご教授お願い申し上げます

  • WindowsMeのコンベンショナルメモリ

    WindowsMeのMS-DOSプロンプトでコマンド「MEM」を使ったところ 最大実行可能プログラムサイズ 531K (543,840 バイト) このように表示されます。 この空きメモリの容量を増やす方法をご存じ有りませんか。  DOSプログラムが空きメモリ容量を570KBほどを要求してきます。 PIFファイルのメモリの設定で600KBに設定しても、 『現在のシステム設定では、このプログラムに必要なコンベンショナル メモリは確保できません。  コンベンショナルメモリを使っているドライバまたは常駐プログラムを アンロードするか、プログラムのプロパティシートで合計コンベンショナルの 値を減らしてください』と表示されます

  • 共有メモリ方式とメッセージパッシング方式

    並列処理をプログラムで記述する方法について調べていて、共有メモリ方式とメッセージパッシング方式というものを見つけました。ただ、この2つについて何がどう違うのかがうまく理解できません。ぜひおしえてください。

  • 仮想メモリのセッティング

    メモリを256MBから1.12GBに増設したのですが、仮想メモリの初期サイズや最大サイズの値をどのように変更したらよいですか?

専門家に質問してみよう