このページの本文へ

ここから本文

2024年度 三菱電機ソフトウエア技術レポート

価格競争力強化のための再利用可能ソフトウェア資産の開発

【執筆者】

電子システム事業統括部 通信機事業所 通信技術第二部 ソフトウエア基盤技術グループ
赤坂 賢洋

【概要】

ソフトウェア開発において、再利用可能ソフトウェア資産の適用は、原価低減・品質向上を直接的に実現する有用な方法である。当社では、通信・組込みソフトウェア開発への適用を指向した再利用可能ソフトウェア資産の開発・整備を2023年度に実施し、2024年度にその適用を実践した。本稿は、その内容と適用効果を述べる。

1.まえがき

ソフトウェア開発において、顧客に提供するシステムの価値を維持しつつ開発費を削減する最も効果的な手段は、ソフトウェア再利用により開発規模を下げることである。そのために、BU(ビジネスユニット)に合った再利用可能ソフトウェア資産を保有することが肝要である。

このゴールを主目的として、当部門では2023年度、再利用可能ソフトウェア資産の開発を実施した。本稿ではその内容と成果、さらに実開発への適用効果を述べる。

なお、本稿は技術報告のため、資産に関する権利、価格については言及しないことを了承されたい。

2.課題とモチベーション

当部門では、顧客に対し、主として通信機器に搭載するソフトウェアを提供している。通信分野は競合他社が多く、顧客は厳しい価格競争にさらされている。そのような状況で、当社としても顧客の価格競争力向上を支援するため、ソフトウェア開発費の低減が必要となっている。

また顧客製品は社会インフラを担うものが多く、品質要求は高い。品質(Q:Quality)に問題が生じると、それは直ちにコスト(C:Cost)、納期(D:Delivery)に悪影響を及ぼす。そのため品質の確保は、当社として重要な課題である。通信ソフトウェアに利用できるOSS(Open Source Software)も存在するが、汎用性を重視していることから自由度が高く、設計の統制に労力を要する。また機能が多く、コードも大規模であることから、保守や品質責任の観点で重荷になるケースがある。

別の視点からは、組込み開発では開発サイクルとしてビルド⇒実機へのプログラム書き込み⇒テスト、が必要であり、汎用PC(パーソナルコンピュータ)やクラウドに搭載する場合と比べそのサイクルに時間を要する。これゆえソフトウェアに起因する問題は、可能な限り実機に搭載する前に検出・是正したい要求がある。

これら3つの課題、すなわち ①原価低減、②品質確保、③不具合除去のフロントローディング、に対する解決策を、当部門では表 1のように整理した。

表1 ソフトウェア開発の課題と解決策

課題 解決策
原価低減 《再利用による開発規模低減》
再利用可能資産を用い、開発規模を低減する
品質確保 《アーキテクチャの再利用》
ベストプラクティスなアーキテクチャを再利用することにより、設計崩れを抑止する
不具合除去のフロントローディング 《プラットフォーム差異吸収》
実機試験の前に汎用OS(オペレーティングシステム)環境での機能試験を可能とするため、プラットフォーム差異を吸収する再利用可能資産を準備する

各々の解決策について、次節より詳述する。

2.1 再利用による開発規模低減

ソフトウェアの開発コストは、一般に開発規模の増加に伴い増大する。また、開発規模の増加は開発リスクも増加させるため、リスク対策費も積み重なる。このため開発規模の削減は、直接的に開発コスト低減効果をもたらす。

2.2 アーキテクチャの再利用

ソフトウェア開発において、「機能」はプロダクトにより千差万別である。一方で、主として非機能要件を実現する「ソフトウェアアーキテクチャ」(以降、本稿では「アーキテクチャ」と略す)は、プロダクトが異なっても同じものを採用することが多い。より広範囲なプロダクトでソフトウェアを再利用するために、当部門ではここに着目した。

そこでまず、過去13年にわたる開発180案件で採用したアーキテクチャを調査し、表2の5つの類型に分類した。

表2 アーキテクチャ分類

分類 説明
サーバアーキテクチャ 外部からの入力を処理ハンドラに振り分け、イベントドリブンで処理するアーキテクチャ
例:通信システム監視制御サーバ
GUIアーキテクチャ GUI(Graphical User Interface)をもつクライアントアプリケーションのアーキテクチャ
定周期処理アーキテクチャ 定周期にリアルタイム処理を行うアーキテクチャ
例:ハードウェア制御ソフトウェア
プロトコル実装アーキテクチャ プロトコルスタックを終端するためのアーキテクチャ
例:通信プロトコルレイヤ
その他 上記に該当しないアーキテクチャ
例:単一スレッドで動作する単純なツール等

各アーキテクチャの名称は一般的なものではなく本調査において独自に命名したものであるため、詳細は4章で説明する。これらのアーキテクチャの採用割合を集計したところ、表3のとおりとなった。なお、本表は当部門で主として用いられる、C/C++言語を用いた開発案件に限って集計した。

表3 アーキテクチャ採用割合(C/C++)

No. アーキテクチャ 割合[%]
サーバアーキテクチャ 44.3
GUIアーキテクチャ 20.8
定周期処理アーキテクチャ 16.1
プロトコル実装アーキテクチャ 11.5
その他 7.3

この調査から、再利用可能資産として、①サーバアーキテクチャ、③定周期処理アーキテクチャ、④プロトコル実装アーキテクチャの3種に対応することとした。これにより、C/C++開発(当部門全開発の75.0%)の70.9%で利用でき、かつ他の言語を含めても53.1%、つまり半数以上で利用できることとなる。なお②GUIアーキテクチャについては、採用するGUIフレームワークで多くの場合アーキテクチャが規定されるため、対象外とした。

2.3 プラットフォーム差異吸収

組込み開発において、不具合除去をフロントローディングするため、当部門では実機試験の前に、汎用PC上で機能試験を行うことが多い。そのためには、プラットフォームごとに試験環境を用意する必要がある。

そこで、再利用可能資産にプラットフォーム差異を吸収する層を設ける。具体的には、実機で採用されることが多い複数のOSについて、POSIX(Portable Operating System Interface)のように共通したインタフェースを提供することを計画した。これにより、機能試験までの工程をWSL(Windows Subsystem for Linux)等の汎用Linux環境で実行できるようになる。

3.再利用可能ソフトウェア資産の設計

図1 再利用可能資産層構成

図1 再利用可能資産層構成

前章の考察から、保有するべき再利用可能資産に求める要件を以下のように定めた。

  • ① OSの差異を吸収する層をもつこと
  • ② サーバアーキテクチャ、定周期処理アーキテクチャ、プロトコル実装アーキテクチャを簡便に実装できること

そのため再利用可能資産の設計を、図1のような層構造をもつものとした。実装には、部門で最も頻繁に用いられるC/C++言語を用いた。資産の名称は、FRA(Fundamental Reusable Assets)とした。

まず最下層に、C言語で実装するプラットフォーム差異吸収層を配置する。これをFRAcと称する。C言語のみで実装するため、C++コンパイラは不要である。上位層への依存もない(依存関係は常に上から下のみとする)ため、C言語による開発シーンでは、本層単独でも使用できる。

その上にC++のクラスライブラリを配する。この層を狭義のFRAと呼ぶ。クラスライブラリの最下層には、FRAcをオブジェクト指向的にラップする“System”パッケージを置く。これにより、FRAc単独で使用する以上の利便性を開発者に提供する。本パッケージとFRAcで、「プラットフォーム差異吸収層」を構成する。

クラスライブラリの最上位には、前章で述べた各アーキテクチャを容易に実現するため、高水準な「再利用アーキテクチャ層」を設ける。この層は、単一の“Application”パッケージにより構成する。

最上位層とプラットフォーム差異吸収層との間には、プラットフォームに依存しない共通部品を配する。この「共通部品層」は、ネットワーク処理を集めた“Network”、低水準な組込み開発でも利用可能なコンテナをもつ“Container”、その他共通的に利用するクラスの集合である“AppCom”の3つのパッケージを収容する。

これらをもって、FRAの全体像とする。詳細な機能の一覧は、付録に記載する。

4.FRAによる各種アーキテクチャの実現

本章では、2章で述べた各種アーキテクチャを、FRAを用いることによってどのように実現するか、例を示しながら述べる。

4.1 サーバアーキテクチャの実現

図2 サーバアーキテクチャの例

図2 サーバアーキテクチャの例

サーバアーキテクチャは、当部門で開発するソフトウェアで最も頻繁に採用される。同アーキテクチャでは、外界からの入力(イベント)を受信すると、その種別に応じた処理ハンドラにイベントを振り分ける。イベントを受けた処理ハンドラは、内部状態を更新しながらそれを処理し、必要に応じ応答を送出する。内部状態はメモリ内のテーブルやデータベースのほか、組込み開発では専用ハードウェアの制御もこれに相当する。図2に構成例を示す。なお、図2では3層アーキテクチャで描いているが、層構成の制約はFRAにはない。

図3 サーバアーキテクチャの実装例

図3 サーバアーキテクチャの実装例

FRAは、イベントを受け付けるキュー付きスレッドを具備する。これを「サービス」と呼び、実装ではApplication::Serviceクラスに対応する。プレゼンテーション層のインタフェーススレッドやビジネスロジック層の処理ハンドラは、同クラスをサブクラス化して実装する。コード例を図3に示す。なお、図3では、サブクラス化した個々のサービスのコードは省略している。

開発者は、実装した自身のサービスをインスタンス化し、Applicationクラス(Application::Application)に追加する。アーキテクチャ設計のアウトプットとコードを直感的に結び付けて実装できるのが特徴である。サービス間に依存関係はなく、任意のサービス間でメッセージを送受信できる。送信時には、メッセージプール(AppCom::ContentFactory)からメッセージバッファ(AppCom::Content)を借り受ける。送受信は電文をコピーすることなく、そのポインタのみを受け渡すため高速である。使用し終わったメッセージは、FRAの機構によりプールに自動返却される。このため実装者は、メッセージのライフタイムを管理する必要がない。

各処理ハンドラは静的なスレッドに割り付けてもよいが、そうすると処理ハンドラの数だけスレッドが必要になる。これを回避するため、FRAはスレッドプーリングとその割付け機構を提供する。イベントが入着すると、開発者はイベントと、処理する制御ハンドラを組にしてスケジューラ(AppCom::Scheduler)に渡す。制御ハンドラにすでにスレッドが割り当たっている場合、スケジューラはイベントを制御ハンドラにキューイングする。割り当たっていない場合は、スレッドプールからスレッドを借り受け割り当てる。これにより、少ないスレッド数で多数の制御ハンドラを駆動できる。

この機構は、非同期並行動作する状態コンテキスト(AppCom::Context)にも応用できる。例えば携帯電話基地局では、1基の基地局で万単位のUE(User Entity)を制御する。その全てについて状態管理が必要であるが、このような場合でも、本機構を用いれば、CPU(Central Processing Unit)のコア数に合わせた本数のスレッドで全てのUEに対向できる。

4.2 定周期処理アーキテクチャの実現

図4 定周期処理アーキテクチャの処理タイミング例

図4 定周期処理アーキテクチャの処理タイミング例

定周期処理アーキテクチャは、制御系システムでよく用いられる。定周期(40msや5ms等)に呼び出されるコールバック関数内の処理で、主としてハードウェアを制御する。コールバック関数の駆動は、リアルタイムタスクで行う。非周期・非リアルタイムなタスクと組み合わせる場合もある。その場合、それらのタスクはリアルタイムタスクより優先度を下げ、リアルタイムタスクが動作していないCPUの空き時間に実行する。図4は、定周期処理アーキテクチャに基づき、専用ハードウェアによりデータを送受信するソフトウェアの処理タイミング例である。

図5 定周期処理アーキテクチャの実装例

図5 定周期処理アーキテクチャの実装例

FRAを用いると、定周期処理は簡単に実装できる。System::CycThreadをサブクラス化し、それをアプリケーションに追加すればよい。実装例を図5に示す。定周期に実行したい処理は、オーバライドしたRun()メソッドに実装する。

定周期処理アーキテクチャにおいて、定周期処理の実行時間が周期を超える「オーバラン」は深刻なエラーとなる。CycThread::Overrun()メソッドは、それが発生した場合にFRAにより呼び出される。開発者は、必要なエラー処理をここに記述する。負数をリターンすると、FRAはアプリケーションを安全に終了させる。組込みソフトウェアでは、それは通常WDT(WatchDog Timer)のタイムアウトを引き起こし、結果として装置アラーム状態を達成できる。

4.3 プロトコル実装アーキテクチャの実現

図6 プロトコル実装アーキテクチャの例

図6 プロトコル実装アーキテクチャの例

プロトコル実装アーキテクチャは、プロトコルスタックを終端するアプリケーションで採用される。図6は、UDP(User Datagram Protocol)上に構築したプロトコルA、Bを終端するアプリケーションの構成例である。

サーバアーキテクチャ同様、プロトコル実装アーキテクチャでも、各スレッドはApplication::Serviceのサブクラスとして実装する。この例では、「対向装置A IFサービス」がUDPを終端し、「プロトコルAサービス」「プロトコルBサービス」が各プロトコルを終端する。一般にプロトコルは状態をもつため、各サービスも状態管理機能をもつ。例えば対向装置が複数あり、その各々について状態を持たなければならない場合は、4.1章で述べた状態コンテキスト(AppCom::Context)を利用できる。実装例はサーバアーキテクチャと同様のため省略する。

5.FRAのその他の特徴

5.1 完全なメモリ管理

組込み開発では、しばしばRAM(Random Access Memory)領域のアドレスが固定であり、その領域に静的なテーブルを作成してアプリケーションを動作させる。これはC言語では実装容易であるが、C++ではそのオブジェクト指向的特徴を活かしづらく、同言語による実装を避ける原因になる。C言語の単位FP(Function Point)あたりのコード量は、C++の倍(1)であるため、同じ機能を作り込むのに、C言語ではC++の倍のコストを要する計算になる。

プリミティブな組込み開発でもC++を採用しやすいよう、FRAは、動的にメモリ確保する全てのクラスにメモリアロケータを与えられるようにしている。デフォルトではmalloc/freeが動作するが、アロケータにSystem::ProgressivePlacementAllocatorを用いると、全てのC++インスタンスを固定アドレスに割り付けることができる。これにより、オブジェクト指向のメリットを享受しつつ、組込み開発特有のメモリ利用上の制約を遵守したり、動的メモリの確保・解放によるメモリフラグメントといった安定稼働を脅かす問題を回避したりできる。C++を採用するとFRAの全機能を利用できるため、開発規模を大幅に削減できる。

制約として、静的領域に割り付けたいC++インスタンスは、起動時に全て生成する必要がある。組込み開発においては厳格なメモリ管理を求められることが多く、使用するメモリを起動時に一括で確保するアーキテクチャを採用するケースは多い。本制約はこれに準じており、組込み開発エンジニアにも受け入れやすいものである。スタック上に生成するインスタンスに関しては、スタック領域を超過しない限り、制限はない。

5.2 エラー処理の最小化

一般に共通ソフトウェアは、その汎用性ゆえ、しばしばこまめに、かつ詳細にエラーを返却する。そのため開発者側ではエラーハンドリングのコードが増大する。しかし、それらエラーの多くは運用時には発生しない、又は発生を期待しないものである。そのようなエラーに対応するエラー処理コードに付加価値はなく、その開発コストはロスコストと言ってよい。

FRAは、明らかな利用誤りや不具合など、運用時に発生することを期待しないエラーについては、エラーを返さずアボートする。これにより開発者は、書くべきエラー処理コードを最小化できる。この特性により、顧客の投資を真に価値のある「機能」に集中させることができる。アボートを引き起こすような不具合の除去を実機搭載前に開発者に促せるので、不具合除去のフロントローディングも実現できる。

5.3 OSS依存の最小化

FRAはOSSを追加でインストールすることなく利用できるが、一部機能の実現にOSSを利用している。その機能を利用しない場合、ビルドオプションによりOSSを切り離すことができる。これにより、プログラムサイズを小さくできる。切り離した場合のプログラムサイズは、約10MBである。OSSは、ライセンス上利用しやすいものに限定している。

6.実開発での適用効果

2024年10月現在、2件の開発に適用し、1件は顧客に提供済みである。当該案件の担当プロジェクトチームで適用いただいた際の効果を表4に示す。

表4 適用効果

FRAがアーキテクチャ設計をナビゲートしてくれた
サービス間メッセージ送受信の高水準な機能が開発量削減、不具合混入防止両方に役立った
ドキュメントや資料が充実しており、理解の助けになった

担当プロジェクトチームからFRAの適用に対するポジティブな意見を得られたことに加えて、開発規模削減についても効果を確認することができた。結果、短工期、安定稼働、応答性能の改善を実現することにより、顧客にもメリットを提供することができたと考える。

7.むすび

本稿では、当部門におけるソフトウェア開発の課題を整理し、その課題を解決すべく開発した再利用可能ソフトウェア資産“FRA”を紹介した。今後も継続して適用を推進するとともに、さらなる機能向上・改善を続ける予定である。

付録

■FRAc機能一覧
条件変数、時刻関連ユーティリティ、定周期スレッド、組込みタイマ、ファイル、IDプール、ロガー、メモリバッファ、Mutex、ネットワークインタフェース操作、ロールバッファ、ソケット、ソケットサーバ、文字列操作、スレッド、タイマ、etc.

■FRA機能一覧(FRAcのラッパー除く)
メモリアロケータ、連番生成器、IP通信関連機能、各種コンテナ、ジョブ、スケジューラ、メッセージバッファ関連、状態コンテキスト、キュー付きスレッド、スレッドプール、同期待ちオブジェクト、アプリケーションテンプレート、コマンドライン解析、設定ファイル解析、サービス、サービス間メッセージ関連、etc.

商標

  • ・Windowsは、米国Microsoft Corporationの米国及びその他の国における登録商標である。
  • ・Linuxは、Linus Torvaldsの日本及びその他の国における登録商標である。

参考文献

筆者紹介

  • ■ 赤坂 賢洋(アカサカ ノリヒロ)

    1993年入社。防衛・通信・医療画像・バイオインフォマティクス関連業務を経て、2003年より通信・組込み機器のソフトウェア開発事業に従事。現在、電子システム事業統括部通信機事業所 通信技術第二部 ソフトウエア基盤技術グループ、及び技術統括部 開発部 AI技術推進室に所属