0

私は Fortran90 でライブラリを作成したいと考えており、これを行うにはパブリック ルーチンをファイル interface.f90 (モジュールなし) に収集し、すべてをコンパイルして ".a" スタティック ライブラリに収集するのが適切な方法であると考えました。また、interface.f90 のルーチンに対応するインターフェース ブロックを含むファイル interface.inc を維持します。次に、interface.inc と一緒に .a ファイルを配布します。これにより、ユーザーは「include 'interface.inc'」を使用してコンパイル時に型チェックを行うことができます。

問題は、ライブラリを開発するときに、パブリック ルーチンのインターフェイスが変更されるたびに、interface.f90 と interface.inc の 2 つの場所で手動でチャンスを作らなければならないことです。最良のケースは、ライブラリのコンパイル時に interface.f90 から interface.inc を自動的に生成できることですが、これまでのところ、標準化された方法は見つかりませんでした。

ただし、ライブラリのコンパイル時に矛盾が検出される限り、interface.inc を手動で変更してもかまいません。だから私が求めているのは、interface.incのインターフェイスブロックとinterface.f90にある実際のルーチンの一貫性を(ライブラリをコンパイルするときに)自動的にチェックする方法はありますか?

4

1 に答える 1

1

Fortran 90 の言語の意味ではありません。特定のプロセッサが診断機能としてこれを提供する可能性がありますが、必須ではありません。

自動インターフェイス生成に関しては、適切なコマンド ライン オプションを備えた、私が認識している 1 つのプロセッサ (Intel Fortran) は、遭遇する外部プロシージャごとにインターフェイス ブロックを書き出します。これは、外部プロシージャのインタフェース チェックに使用されます。あなたと同様の理由でこれらのインターフェイス ブロックを収集するユーザーを何人か見てきました。ただし、これは非常にプロセッサ固有の動作に依存しており、その動作が時々変更されると、この配置が崩れることがあります。

Fortran 2003 では、一貫性チェックの可能性存在する可能性があります。このアプローチは、別のモジュールで、インターフェイス ブロックに基づいてプロシージャ ポインターを宣言します。次に、各実際のプロシージャー内で、モジュールをプロシージャー・ポインターと共に使用し、(おそらく、デバッグの if 構造内などで) その関連するプロシージャー・ポインターを実際のプロシージャーに関連付けようとします。コンパイラは、プロシージャ ポインターの明示的なインターフェイスの不一致を診断する必要はありませんが、ほとんどの場合必要です。ディスカッションについては、このフォーラム スレッドの最後にある投稿を参照してください(F2008 標準には、プロシージャ ポインターの割り当てについて正式に「解釈を提供できない」というエラーがあることに注意してください。ただし、正誤表 2 で修正されると思います)。

インターフェイス ブロックをエンド ユーザーにパッケージ化するという点では、それらをモジュールに入れ、そのモジュールのソースを提供することを検討してください。これにより、将来ユーザーに提供できる内容の柔軟性が大幅に向上します。

MODULE interfaces
  IMPLICIT NONE
  PRIVATE
  PUBLIC :: external
  INTERFACE
    SUBROUTINE external(arg)
      IMPLICIT NONE
      INTEGER, INTENT(IN) :: arg(:)
    END SUBROUTINE external
  END INTERFACE
END MODULE interfaces

MODULE proc_pointers
  USE interfaces
  IMPLICIT NONE
  PRIVATE
  LOGICAL, PARAMETER, PUBLIC :: check_flag = .TRUE.
  PROCEDURE(external), POINTER, PUBLIC :: external_pptr
END MODULE proc_pointers

SUBROUTINE external(arg)
  USE proc_pointers
  IMPLICIT NONE
  INTEGER, INTENT(IN) :: arg(:)
  IF (check_flag) external_pptr => external
  ...    
END SUBROUTINE external
于 2013-02-21T22:57:05.240 に答える