No.2ベストアンサー
- 回答日時:
どちらかというと, 普通は reentrant な関数というような気はします (reentrant は形容詞, reentrance は名詞) が, ISO の仕様として C の標準ライブラリはどれもリエントラントであることが保証されません. 従って, 一般にシグナルハンドラで標準ライブラリを呼び出すことはできません (と, ちゃんと規格に書いてあります).
もちろん処理系によってリエントラントであってもかまいませんが, リエントラントであることを前提としたプログラムは移植するときに問題となりえます.
再入可能であることは、保証されていないということですね。
その結果、割り込みでは使用してはいけない・・・と理解しました。
リエントラントが形容詞なら、それに「な(断定の助詞の連体形)」は付けることはできませんね。
リエントランスは名詞(体言)なので「な(断定の助詞の連体形)」は付けることができますが。
リエントランス関数とは言えないけど、リエントラント関数とは言えますね。
No.6
- 回答日時:
処理系に依存するので, 特定の標準ライブラリ関数がリエントラントかどうかを調べるにはその処理系の資料を読むしかないです. まあ, 明らかにリエントラントでない標準ライブラリ関数はありますが.
念のためですが, 規格では
「標準ライブラリ関数がリエントラントであることを保証しない」
The functions in the standard library are not guaranteed to be reentrant
つまり「リエントラントであってもいいしリエントラントでなくてもいい」であって, 「すべて非エントラント」であると規定しているわけではありません>#4... もちろんプログラムを書く上では (すべての関数がリエントラントでないことを想定しなければならないので) 実質的に同義ですが, そんな規定はだれにとっても困るだけ.
> 処理系に依存するので,
処理系依存のプログラムは書きたくないので、処理系依存の部分は排除したいと思います。
ただ、OSを設計(模倣)していますので、どうしてもマシン依存=処理系依存があるのですが、最低限に抑えたいのです。
>「標準ライブラリ関数がリエントラントであることを保証しない」
ということで、再入可能ではないことを前提に設計して行きたいと思います。
リエントランス・リエントラントについては、#2のお礼を見てください。
No.5
- 回答日時:
追記。
ANo.4の回答では「fopenは非リエントラントな関数」と回答しましたが、実装を工夫し、以下のようにすれば「リエントラントな関数」になります。
・システムコールでファイルを開く
・ファイルがオープン出来なければエラーで帰る
・割り込み禁止にする
・ファイル識別子の空きを探し、空きが無かったら、ファイルを閉じ、割り込み禁止解除をして、エラーで帰る
・空きがあったら、それを使用済みに書き替える
・割り込み禁止解除し、ファイル識別子のポインタを戻り値にして帰る
これで「空きを探して、使用済みに変え、それを返す」までの間、他のスレッドや割り込み処理ルーチンに切り替わる心配はないので「リエントラントな関数」となります。
とは言え「使っているコンパイラのfopenが、こういう親切な実装をしてくれてるかどうかは、実際に実装した人にしか判らない」ので「使う側は、非リエントラントだと思って、安全な使い方をするしかない」のです。
OSの設計をしているので、OS依存の関数を使うことはないのですが、
> とは言え「使っているコンパイラのfopenが、こういう親切な実装をしてくれてるかどうかは、実際に実装した人にしか判らない」ので「使う側は、非リエントラントだと思って、安全な使い方をするしかない」のです。
この方針で行くことにしました。
No.4
- 回答日時:
「リエントラント」ですね。
基本的には「その関数が終了して呼び出し元に復帰する前に、誰かが同じ関数を呼んだ場合、正常に動作するかどうか?」で「リエントラントな関数」か「リエントラントでない関数」かが決まります。
通常、静的メモリを操作しする関数は「リエントラントでない関数」と思って間違いありません。
例えば、fopenは、静的メモリに配置された「ファイル識別子」を返します。簡単に言えば「FILEへのポインタ」です。なので、fopenは「リエントラントでない関数」です。
fopenは、未使用のファイル識別子を探し、空きがあれば、システムコールでファイルを開き、開けたら、ファイル識別子を使用済みに書き替え、そのファイル識別子を返します。
この処理が「2つのスレッドで、ほぼ同時に起こった」としたら、どうなるでしょう?
1.スレッド1でfopenを呼んだ。
2.スレッド1は、静的メモリに配置された未使用のファイル識別子を探し、5番に空きがあったので、システムコールでファイルを開こうとした。
3.システムコールが呼ばれたので、スレッド2に切り替わった。
4.スレッド2でfopenを呼んだ。
5.スレッド2は、静的メモリに配置された未使用のファイル識別子を探し、5番に空きがあったので、システムコールでファイルを開こうとした。
6.システムコールが呼ばれたので、スレッド1に切り替わった。
7.スレッド1が呼んだfopen関数は、ファイルが開けたので、5番を使用済みにして、5番のファイル識別子を返した。
8.スレッド2に切り替わると、スレッド2が呼んだfopen関数は、ファイルが開けたので、5番を使用済みにして、5番のファイル識別子を返した。
このように、2つのスレッドのfopenで「同一のファイル識別子(上記の例では5番のファイル識別子)を返されてしまう」ので、動作が不安定になります。
本当であれば、fopenを呼んだ順に、5番、6番のファイル識別子が返されねばなりません。
で、仕様上は「C標準ライブラリ関数は、すべて非エントラント」ですが、処理系によっては、実装の際に「エントラントな関数」として実装される事もあり「事実上、エントラントか非エントラントかは、処理系に依存する」と言うのが現状です。
> 通常、静的メモリを操作しする関数は「リエントラントでない関数」と思って間違いありません。
この点がポイントになることは、解っていました。
さて、どの関数が静的領域をいじるのか?
それを調べる方法は果たして存在するのか?
仕様で決められていれば楽なのに・・・。
と言った所です。
ですので、
> で、仕様上は「C標準ライブラリ関数は、すべて非エントラント」ですが、
で、解決です。
リエントランス・リエントラントについては、#2のお礼を見てください。
No.3
- 回答日時:
「リエントラント(再入可能)」な関数
とは、当該関数実行中に、他のスレッドなどからさらに実行が可能
な実装仕様を言います。一般にWindowsのコールバック関数及び一
群のメッセージ処理関数群はリエントラントであることが要求され
ていますが、そうでなくても再入しない場合がほとんどなので動い
ちゃいます(笑)。但し、DLLの関数はリエントラントであることが
より強く要求されます。
似たように言葉に「リカーシブ(再帰可能)」がありますが、こちら
の条件は当該関数から当該関数をコールしても動作することです。
ニーモニックレベルだと「リロケータブル」というのも良く言われ
ますが、特別に処理しない限り、C言語では全てリロケータブルに
翻訳されます。
今回は、OSの設計でぶつかった問題でした。
なので、パソコンのOS類のお世話にはならない訳ですが(組み込み系の設計です)、DLLが再入可能である必要があることは、良く解ります。
リロケータブルは、ちょっと今回の件とは関係ないような・・・。
リエントランス・リエントラントについては、#2のお礼を見てください。
No.1
- 回答日時:
thread safe で検索すればわかると思います。
昔はリエントラントと言ってましたね。SUN4あたりからそういう用語が出てきたかと。
The GNU C library uses thread safe functions by default and libc5 used non thread safe versions.
これはなんか gcc のlibcが遅いとか言う苦情にたいする反論。
コンパイラにオプションがあったりもします。
言語によってはリエントラント関数にはなにか特別な識別子があったりもします。 今思い出せない。
参考書よりも検索しまくりでどうぞ。
> thread safe で検索すればわかると思います。
> 参考書よりも検索しまくりでどうぞ。
検索用キーワードを教えていただいたので、検索かけてみます。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- 統計学 直線の傾き(回帰係数)から相関係数を計算できるのでしょうか? 2 2022/09/16 19:28
- 物理学 座標変換に関して質問です。参考書に 「力は一般に時間と場所によって異なるから力f(ベクトル)はx,y 3 2022/07/03 20:24
- 日本語 方言は無くなるべきですか。 皆さん、こんにちは。日本語を専攻しているスペイン人のパウです。最近、日本 8 2022/05/11 19:52
- 副業・複業 『Webライター』になりたいです。 まずブログSNS副業に興味関心がありました。 そして大きな目標と 14 2023/06/16 14:01
- Excel(エクセル) Excel 参照元の値を参照したい 1 2022/08/20 18:58
- Excel(エクセル) Excel処理について、教えて下さい。 下記表は、サンプルです。(実際には千件以上あります) A列に 6 2023/03/16 18:21
- Excel(エクセル) エクセルでの文字抽出 3 2022/07/09 12:17
- その他(家事・生活情報) 関西人だけど関西弁が苦手 3 2022/04/03 13:21
- 哲学 なぜ議論の場において言葉遊びをしてしまう人達がいるのでしょうか? 銃社会のアメリカでよく聞かれるのは 9 2023/06/17 22:38
- その他(悩み相談・人生相談) みんなの前で、自分の意見が言えません。 私が意見を言ったところで、なんにもならない。私の意見に何か言 7 2023/04/06 17:48
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
画像読み込み時のOutOfMemory
-
C言語初心者の質問失礼します。
-
csvファイルを開かずに文字を検...
-
ファイル名の先頭にアンダース...
-
C言語関数違いについて。
-
アドレス帳WABファイルをサンダ...
-
テキストファイルの最終行を削...
-
VC++の外部依存関係
-
「VBScript」ADODB.Streamにお...
-
SGファイルって何ですか?
-
VBに、Cのincludeのようなもの...
-
分割コンパイルの#defineについて
-
C言語のfopenについて教えてく...
-
PHPのソースの追いかけ方
-
マウスポインタの変更
-
エクセルVBAでフォルダ内の重複...
-
fopenできる上限の変更
-
リエントランスな関数
-
2つのテキストファイルのマー...
-
VBAにてEXCEL以外のファイル(テ...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
dataファイルをxtxファイルにす...
-
C言語初心者の質問失礼します。
-
csvファイルを開かずに文字を検...
-
ファイル名の先頭にアンダース...
-
大きいサイズのテキストファイ...
-
テキストファイルの最終行を削...
-
ドラッグアンドドロップでファ...
-
グローバル変数のよくない使い...
-
CSVファイルへの保存の際、デー...
-
ファイルの結合
-
SGファイルって何ですか?
-
VBに、Cのincludeのようなもの...
-
XMLファイルの表示について
-
分割コンパイルの#defineについて
-
ハッシュの計算時間について
-
バッチで118項目のCSVを処理し...
-
RPGでファイル名(もしくはレコ...
-
Excelマクロでの再読込み方法
-
C言語のfopenについて教えてく...
-
COM相互運用機能のON,OFFによる...
おすすめ情報