2015-08-26

要求分析と安全設計との関係(機能安全の致命的な欠陥)

日本の組込み系のソフトウェアエンジニアに担当製品に対するユーザー要求は何かを聞くとすぐさま答えられないことが多い。

顧客の要求に基づき日々ソフトウェアを開発しているIT系のソフトウェア技術者には驚きかもしれないが、事実そうなのだ。

なぜ、組込み系のソフトウェアエンジニアは自分の製品のユーザー要求を答えられないのか。それは、過去の製品のソフトウェアを追加、修正しながら新しい製品を作っているから、大元のユーザー要求を把握していなくとも、製品開発が出来てしまうからだ。

継承するソフトウェアの中に基本機能、基本性能がすでに入っているから、付加機能を付け足すぶんには元の要求を知らなくても作業はできるのだ。

さながら、老舗旅館の旧館、新館、別館、アネックスといったようなもので、結果、継ぎ足しで成り立っている迷路のような構造になることもしばしばだ。

継ぎ足し、修正ばかりやっているソフト技術者はユーザー要求は即答できなくても、機能については詳しいし、饒舌に説明できる。

さて、この機能仕様ドリブンのソフトウェア設計は、安全を考慮しなければいけない機器にとっては、致命傷になる危険がある。

なぜか。ひとつはソフトウェアシステムが複雑化していった際に、機能同士が背反する関係になる可能性があるからだ。よかれと思って付けた付加的な機能が、基本機能に悪い影響を与えることがある。

医療機器の世界では、リスクコントロール手段を設計する際には、リスクコントロール手段によって生まれる新たばリスクを分析せよという規格要求がある。

例えば、異常を検出するハード・ソフトを追加して、異常検知したら装置を停止するようにしたとする。異常は滅多に起こらないから問題ないと考えて、十分な負荷試験をせずにリリースする。確率は低いものの、異常の誤検知が起こり正常なのにシステムが止まることがあったとすると、ユーザーからの大クレームになる。リスクコントロール手段を追加すると、何かしら別のリスクが生まれるのだ。

多くの自動車の部品屋さんは、自分の部品に故障検出回路を付けることが機能安全に貢献し、ASIL-D を満たせるのだと言っているようだが、それって本当に木を見て森を見ずだと感じる。故障検出回路という山火事検知装置に対処するソフトウェアを大量に追加することによって、森の複雑度はどんどん上がっていき、本当に火事が起こったときに消防隊が現場に行くための経路が分かりにくくなる、これが機能安全の致命的な欠陥だ。(何の危害を防止するためのリスコントロール手段か分かっていないで安全に貢献するはずだと思い込んで機能を追加しようとするとこうなる)

「これからは故障検出を追加してシステムを冗長にし、動作し続けることが重要だ」といった意見を聞くことがある。冗長設計は安全設計の方法のうちのフォールトトレランスに分類される。安全を実現するための方法の一つだが、欠点はシステムを複雑にする点だ。システムが複雑になると、レアなテストケースが出てきて、滅多に起こらないシーケンスで不具合が作り込まれる危険性が生まれる。ハードウェアならば安い部品を冗長化するよりも高信頼性部品を使って、シンプルな構造にする方を選ぶこともあるだろう。ソフトウェアならば、シンプルなアーキテクチャにして、テストしやすくするという選択肢もある。冗長化すればいいというもんではない。何を防ぎたいのかを頭に置いた上で、ハード・ソフト含めどんな安全設計が最適かを選ばないといけない。フォールトトレランスだけが解決策だと思っていると、システムの複雑化からくるリコールのリスクを負うことになる。

こういったシステムの複雑化に伴う問題を最小限に抑えるためには、システムに対するユーザー要求をしっかりと優先順位を付けて分析しておく必要がある。重要な要求とあってもなくてもよい付加的な要求は分けて認識しておかないといけない。そして安全に関する要求など、重要な要求は常に優先度の高い要求として認識しておく。要求の優先度を十分に理解した上で、アーキテクチャ設計を行い、安全アーキテクチャは機能を付加しても崩さないようにしないといけない。

複雑化の影響を自動車で言えば、プリクラッシュセーフティをエンジニアが基本機能に対する付加機能だと考えていると危ないなあと思う。

「障害物を認識したら、自動でブレーキを働かせるという機能を基本機能に付け加えて実装すればよい」と考えるのは危ないと思うのだ。

ユーザーが自動車に求めていることは何か。移動や物の運搬が真の目的なら、どこでもドアが発明されたら、自動車は必要なくなる。(論理が飛躍していると思ったらこちら「洗濯機メーカーは洗濯機を開発してはいけない」を参照のこと)

移動する(安全に移動する)ということはどういったことか。移動したいというユーザー要求はある。ただ、その裏側には安全に移動したいという潜在的な要求がある。移動する時に10回に1回怪我をするようなことはゴメンだと誰もが思うだろう。

安全に移動するという要求を実現する手段に自動車があると考えておくと、システムが複雑化して難しい判断に迫られたときに、答えが見えてくる。

さて、どこでもドアはまだ発明されないとして、移動、運搬をする際に、自分や他人や他の車、設備に損害を与えたくないと誰もが考える。特に、自分自身や他人を傷付けたくない。自動車は運動エネルギーを持って動くのでリスクの潜在的な源(ハザード)を持つ。

プリクラッシュセーフティ機能が稼働するシーンはさまざまある。自動ブレーキを働かせたことで、後続車両から追突されたら、結果的に搭乗者の安全は確保されないかもしれない。(「ISO 26262との向き合い方 (11) ASILの分解は本当に可能か」を参照のこと)

このケースでは「プリクラッシュセーフティ」という機能を実装することを目的にしてはいけない。安全に移動するという要求を満たすために何をすればよいのか、今の技術で何ができるのかを考える。機能より要求は上位にあり、要求はよっぽどのことがないと変わらないが、時代とともに技術は変わっていくので、要求を満たす技術はその時々で変化していく。技術やユーザーの意識の変化によって要求を満たせるレベルも変わっていく。

機能だけに着目していると、その上位にある要求が満たせていなかったり、要求のレベルが変わっていることに気が付かない。

また、機能を追加すればよいと考えていると、安全に対する優先順位が分からなくなってしまう。「機能」のことだけ考えていると、そのシステムに求められる本質的な要求が飛んでしまい、本質的な要求に背反するようなシステムを作り込みかねない。

障害物を発見したらブレーキを作動させるという機能を追加しようとすると、搭乗者の安全を確保するという要求が飛んでしまう。(通常は安全に寄与するが、別な条件では安全を脅かすというケースで、大抵は確率が低いから、事故が起きてから分かる。)

だから、ユーザー要求に基づいたバリデーションが大事なのだ。分業が進んでいる欧米のソフトウェア開発では、バリデーション、バリデーションとこればっかり言われることがある。少人数で人の入れ替わりがほどんどない日本の伝統的な組込みソフトウェア開発では、プロジェクトメンバーみんなが言われなくてもユーザー要求は常に頭の中にあるので、何を確認すれば妥当性を確認できるのか分かっていた。

問題が起こる確率は低いから、漏れなく妥当性を確認することに超したことはないが、必ず漏れはあるので、最も起きてはいけない問題から順にそれらが起きないことを確認していく。そうすれば、問題が起きても大問題ではなく、小問題に押さえ込むことができる。ゼロにしようと思うと穴が生まれる。

私は私、あなたはあなた、私が作った物の責任は私が取るが、あなたが作ったものは知らないというシステムでは、ユーザー要求に基づいた、妥当性確認を行わないと、要求と背反するような物になっている危険性がある。

大規模化したソフトウェアシステムにおいて、日本の多くの組込みソフトがトップダウンで十分な要求分析を経て開発されていないとすると、その危険性が増大する。

じゃあ、どうすれば良いかと言えば、今ある機能や性能を整理しながら、ボトムアップで要求がなんであったかを分析し、概ね要求が洗い出せたら、今度はトップダウンで機能を見直してみる。

こうすれば、アーキテクチャのリファクタリングもできる。

安全に関係しないところであれば、複雑になろうが結合が強かろうがいいだろう。しかし、安全に関わるアーキテクチャは要求がキチンと分析されていないと、機能追加で崩される危険がある。

崩そうと思って崩すのではないからたちが悪い。自動ブレーキの命令をソフトウェアが出せるようになったことで、ネットワーク越しでの自動ブレーキが可能になり、ハッカーにつけ込まれるかもしれない。

ナビの情報と自動ブレーキを組み合わせれば、便利な機能を付加できるかもしれない。しかし、そのお陰で自動車の基本機能や基本性能に悪い影響を与えるかどうかを考えないといけない。

その判断をするためには、システムに対する要求を正確に分析し、要求分析内容が常に確認されている(バリデーションされている)状態にしておかないといけない。

機能を追加してリリースすることがソフトウェア開発だと思っていると、システムが複雑化する中で安全を確保することはできない。

0 件のコメント: