• ベストアンサー

C言語以外ならバッファオーバーフローは起きないのでしょうか?

こんにちわ 私はつい最近プログラミング入門したばかりのものです。 いろいろな興味に実力がついていけずとんちんかんな状態です。 ところで、昨今のセキュリティ問題でよく登場するバッファーオーバーフローという ものは何だろう、と思っていろいろ自分なりに調べてみました。 ある説明文では、C言語のメモリー格納仕様に起因する問題、と書かれていました。 ・・・ということは、パスカルなどのような他の言語であれば、バッファーオーバー フローの心配はしなくてもいいことになるでしょうか? マック愛好家の間では、MacOSの安全性の高さを大変にアピールしていますが、これは 技術的に言うとMacがPascal言語で開発されていたから、という種明かし、と考えれば よいことになりますでしょうか? お暇な方がいらしてましたら、どうかおつきあい頂けましたら幸いです。

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

  • ベストアンサー
  • ultraCS
  • ベストアンサー率44% (3956/8947)
回答No.7

#6です、話がそれて雑談というか余談に近づいていますが ちょっと誤解を招く書き方がありました、コードインタープリタというのは言語ではなく、CPUの中で命令の機械語をフェッチし、インストラクションコードに基づいたアキュムレータの動作、オペランドのアドレス変換をしてデータを取り出す機構で、CPU内部で動く一種のプログラムで、ユーザがいじることは出来ません。コードインタープリタというのも正式名称かはわかりません。 それが、次の実行命令として、インストラクションポインタで指定されたアドレスに格納されているバイト群を取り出すわけですが、このとき、それが、コードかデータかを判断できないと言うことです。 ノイマン型コンピュータでは、アドレス空間はリニアに実装され、そこを適当にコードとデータで分割して使います。この方法にはある程度のルール(低いアドレスは割り込み等のシステムコールに使うなど)はありますが、基本的にはフリーです。データがコードの前にあっても後ろにあっても構わないわけです。 Pascalも、Wirthが考えたPureなパスカルであれば別ですが、現在出回っているPascalは使いやすく(Cと対峙する為もあり)するために拡張が施されているし、実際に使うとなると、すべてを値渡しというわけにも行かず、システムとのインターフェースでは、アドレス渡しをせざるを得ません、で、ここが大きな穴になってしまいます。まあ、BASICだって、ダートマスのPureなBASICは今のBASICとは似ても似つかないものですから仕方ないでしょうけど。 ところで、バッファオーバーフローに限れば、おそらく、プログラムではライブラリで処理しているでしょうから、そのライブラリのコードに問題がある、ところが、そこを書いた人間が退社してしまってわからない。ソースが見つからないなんて事もこの業界ではざらにありますから、おそらく、そんなところではないかと思います。これを書いたプログラマは気が気じゃないだろうなあ(人ごとじゃなく、心臓が縮む思い)。

altosax
質問者

お礼

こんなに沢山詳しく、ほんとにありがとうございます!! なるほど、だんだんわかってきました! こういう図式、と思えばよいわけですね!!(^^)?? 他のご回答者さんもおっしゃるように、 1:Cは配列の境界チェックが甘いとすぐにバッファオーバーフローに直結する 2:だから丁寧なソフトハウスでは厳密に厳しいチェックをして防止に努める 3:しかしプログラマがどんなに頑張ったところでCPU機構内にノイマン式の宿命でデータとプログラムが混同される危険関門がある、 4:C以外の言語の元祖仕様はBOFの発生しない仕様だったが、オーバーヘッド等の弱点改良のためその後仕様変更され、BOFの可能性が同様に生じる仕様になってきている、 ・・・ということになりそうですね? マックファンの主張する「BOFはウインテルの問題」という論理が本当だとすれば、2の「アップルのプログラマが念入りで転出者作成ライブラリのソース引き継ぎ管理もきちんとした社内体制」+3のパワーPCがインテルよりコード解釈を忠実に行う傾向のマシなノイマン式、ということになりそうですね、 こんどは別件でアップルの社内体制や、パワーPCが非ノイマン式に近い解釈動作なのか、ということを質問してみようと思います、 ほんとに皆さんどうも有り難うございました!!! (このスレで私がわかったつもりになったこの解釈で、変なところがありましたら、またどうぞご叱正くださいませ^^お待ちしてます!)

その他の回答 (6)

  • ultraCS
  • ベストアンサー率44% (3956/8947)
回答No.6

一般論で書きますね ノイマン型コンピュータである限り、本質的には回避できない問題です。データとプログラムを区別しないというのも一つの特徴で、これの恩恵はOS開発などでは計り知れないものがあり、ちゃんと理解して使えば大変便利なものでした。インストラクションコードやオペランドを直接書き換えるなど、アドレス空間が小さい時代には大変重宝でした。オーバーレイモジュールなどもユーザー側で実現できましたから。 なので、OSや言語、アプリケーションが一生懸命それを防止しようとしても、最後に出てくるコードインタープリタが一切お構いなしで動いてしまうため、どこかに穴があれば簡単に漏れてしまいます。これはMacでも同じです。違うのは穴の大きさと数ということになります。 また、Macにしても、初期には、OSがPascalで書かれていたとしても、BIOSに当たる部分、ToolBoxやデバイスドライバには68Kネイティブのアセンブラで書いた部分があり、ここでは、同様の問題があり得ました(最近のMacは詳しくないので)。 データフローマシンなど非ノイマン型に期待するしかないかも知れません。実際、アドレス空間が広がった状況では、コードとデータを完全分離することは不可能ではありません。

altosax
質問者

お礼

どうもありがとうございます! >データとプログラムを区別しないというのも一つの特徴で、これの恩恵 なるほど、バッファーオーバーランの悪用という基本の考え方はここに帰結して いるということなんですね^^ >OSや言語、アプリケーションが一生懸命それを防止しようとしても、最後に出てくるコードインタープリタが一切お構いなしで動いてしまうため これはとても興味深いお話をうかがいました! ちょっとかみくだいていただけると嬉しいのですが、 #2&#3のみなさまからお寄せいただいたご回答では、配列の境界チェック を厳密に実施することで未然に防げる(不注意による人災)という主旨で私は 理解したつもりになっていたのですが、コードインタープリターのコンパイラ が、せっかくの厳密な配列の境界のチェックも台無しにしてしまう、という 危険性をノイマン型コンピュータの宿命として持っているということ? になるのでしょうか? わたしはどんなに頑張っても趣味の日曜プログラマまでで終わりそうですが、 概念的な意味では、このあたりが、非常に気になってしまうんです。 >BIOSに当たる部分、ToolBoxやデバイスドライバには68Kネイティブのアセンブラで書いた部分があり なあるほど、また心当たりがありました。 iMac以後のモデルでは、ハードのBIOSが完全に無くなってToolBoxもハードディ スクに格納されるようになったんです(NewWorldMacと分類されています) この問題に起因する事故の防止という意味もあったのかもしれません。 >実際、アドレス空間が広がった状況では、コードとデータを完全分離することは不可能ではありません。 これはありがたい希望の光ですね!

noname#12761
noname#12761
回答No.5

古典的なパスカルの仕様ならバッファーオーバーフローは発生しないかもしれません。 しかしそれでは OS は開発できません。当然ポインタが使用できインラインアセンブラが使えるような拡張された仕様でないと開発はできません。 そうなれば、C,C++ とほとんど条件は変わりません。 また Mac は Unix 指向に向かっていますので関数呼び出しの仕様の違いなど考えると Pascal で開発すると逆にバグが増えそうです。 TT414 さんの >OSX以前はPascalだったかもしれませんが、OSXはCです(unix系なので) との指摘は理にかなっています。

altosax
質問者

補足

どうもありがとうございます、 ちょっとまだ私のレベルでは飲み込めない話なのですが、PascalではOS開発ができない前提ですと、最初のマックがPascalで開発云々、という話は技術的にありえないファンの創作した「神話」のひとつ、となるでしょうか?

  • TT414
  • ベストアンサー率18% (72/384)
回答No.4

>MacがPascal言語で開発されていた OSX以前はPascalだったかもしれませんが、OSXはCです(unix系なので)。

altosax
質問者

補足

どうもありがとうございます。 この辺の事情を私も知りたいのですが、ご存知の方いらしてましたら続報を いただけましたら幸いです。 多分漢字トーク7時代にはCに移行していたのではなかろうか?というフィーリング で私は想像している(多種類のプログラミング環境が揃っていたので)のですが いかがでしょうか、どうぞ皆様よろしくおねがいします!

回答No.3

>ある説明文では、C言語のメモリー格納仕様に起因する問題、と書かれていました。 この説明は適切ではないと思いますよ。 「C言語のメモリー格納仕様を鑑みず、無頓着なプログラミングにより発生する問題」と するのが良いかと思います。 バッファオーバーフローの原因を、C言語に押しつけてしまうのは、如何なものかと。 >・・・ということは、パスカルなどのような他の言語であれば、バッファーオーバー >フローの心配はしなくてもいいことになるでしょうか? 現代のpascal系の言語で、バッファオーバーフローが起こらないわけではありません。 ポインタを使う場面は多々あるので、同じような問題は引き起こす可能性を持っていると 考えたほうが良いと思います。

altosax
質問者

お礼

早速にどうもありがとうございます! >この説明は適切ではないと思いますよ。 >「C言語のメモリー格納仕様を鑑みず、無頓着なプログラミングにより発生する問題」と >するのが良いかと思います。 なるほど、そういうことだったんですね! そうすると、マックファンの方々がマイクロソフトのプログラムを罵倒するのは 単なる身びいきの発言ではなく、ますます現実を冷静に直視した結果の杜撰さの 指摘、ということになりそうですね。 これはマイクロソフトには本当に真剣に抜本的に考え直してもらわないと困る問題ですね! >現代のpascal系の言語で、バッファオーバーフローが起こらないわけではありません。 >ポインタを使う場面は多々あるので、同じような問題は引き起こす可能性を持っていると >考えたほうが良いと思います。 なるほど、パスカルゆえの安全の確保、というのは昔話になってきているのですね! どうもありがとうございました!!

  • rinkun
  • ベストアンサー率44% (706/1571)
回答No.2

No.1さんはOSの不備と言っていますが、多くのバッファオーバーフロー攻撃はOSの用意したバッファじゃなくアプリケーションが用意したバッファを溢れさせてアプリケーションを乗っ取るものです。もしOSの用意したバッファが溢れたらカーネルごと乗っ取られますよ。(^-^;) バッファオーバーフローに関してOSが不備な点は多くはスタック上にあるバッファ溢れ部分でプログラムが実行できてしまうことくらいです。プログラムとデータを区別してアクセス権管理ができていれば多くの場合は防げるんですからね。 # ただOSがCPUサポートなしに管理するのは大変なので最近のCPUではNXビットなんてものが追加されていたりする ちなみにバッファオーバーフローは配列の境界チェックをきちんとやっていれば防げます。C言語では全く無チェックなのでa[-1]なんて無茶もできるわけですが、Pascalや最近ではJavaなど多くの言語では宣言範囲外の配列インデックスではアクセスできないようになっています。 ただ配列インデックスのチェックは実行時のオーバーヘッドになるため、C言語では採用されていないということです。

altosax
質問者

お礼

さっそくに沢山のご回答を寄せていただき感謝感激です! >もしOSの用意したバッファが溢れたらカーネルごと乗っ取られますよ。(^-^;) あっはあ!そういうことですねえ(^^;) >ちなみにバッファオーバーフローは配列の境界チェックをきちんとやっていれば防げます なるほど、アップルファンのみなさんが、マイクロソフトのプログラミングは 杜撰でアップルのプログラマはきちんとしている、という論拠はこの辺にあり そうですね! >Pascalや最近ではJavaなど多くの言語では宣言範囲外の配列インデックスではアクセスできないようになっています。 なるほどなるほど、Javaが言語仕様からして安全だ、と言われている理由も疑 問だったのですが、これで謎が解けました! MacOSではバッファーオーバーフローは起きない、というのはPascalの仕様から 言って本当だったんですね! >実行時のオーバーヘッドになるため これまたなるほど納得です! マックが歴史的にOSが単純な割に非常に重かったのは、そのせいもあった訳で すね。

  • OsieteG00
  • ベストアンサー率35% (777/2173)
回答No.1

C言語に限った話ではないですが、C言語では任意のアドレスのメモリにアクセスできるのでそういう説明になりましたかね。 結局、PascalであってもCであってもコンパイルすれば同じですから、言語による違いというものはありません。また、メモリの格納仕様は処理系(OS)によって異なります。言語仕様によるものというよりは、OS上の不備を突いた攻撃です。OSが用意したバッファより大きいデータ量を送りつけて、バッファより大きい部分のデータをプログラムとして認識させて誤動作させるというしくみです。 Macの安全性については、単にシェアが低くてかつ内容がブラックボックス化しているのでハッカーの興味を引かなかったという事ですね。

altosax
質問者

お礼

さっそくにどうもありがとうございます!! >C言語では任意のアドレスのメモリにアクセスできるのでそういう説明 なるほど、たしかに私の見た説明文も前段としてそのように書かれていました! >結局、PascalであってもCであってもコンパイルすれば同じ なんと、コンパイル後は関係ない話だったのですね^^; おかげさまでわかりました! >OSが用意したバッファより大きいデータ量を送りつけ >ハッカーの興味を引かなかったという事ですね ・・・するとMacに向けて悪い巨大データを送れば理論上はWindowsとおなじく バッファーオーバーフロー攻撃が成立してしまう、ということですね? (しかし実務的にどういう手順で攻撃すればよいか関心が持たれていない、 ∴結果的に今のところ安全、と。) この点については、「できるものならどうぞやって下さい!」と懸賞コンテスト などが行われようとした経緯もありますので、とても気になるところです。 どうもありがとうございました!

関連するQ&A