ユーザ用ツール

サイト用ツール


サイドバー

fortran:ifort

以前のリビジョンの文書です


ifort

  • スパコンで使うことが前提
  • kudpc を参照.

コンパイラオプション

http://accc.riken.jp/HPC/training/text.html

http://www.k.mei.titech.ac.jp/~stamura/NumericalComputation-Tips.html これくらいオプションをつけて実行すれば,だいたいエラーは検出されそう.

ifort -check all -warn declarations -CB -fpe0 -traceback

コンパイラオプションも参照のこと

デフォルトのスタックサイズが小さすぎる

デフォルトのスタックサイズが小さすぎて、-openmpをやるときはスタックサイズを増やしてあげないと、頻繁にセグ落ちする。

!$OMP parallel
write(*,*) KMP_GET_STACKSIZE_S()
!$OMP end parallel

とやると、各スレッドのスタックサイズを返す。これを増やす場合は、最初の!$OMPの前に、

CALL KMP_SET_STACKSIZE_S(size)

とやれば良い。sizeは整数型の変数。所望のスタックサイズ(byte)を書けばよい。

改行の抑制

ifortでは出力時に勝手に改行する仕様になっている。 改行を抑制するためには、Format文を使用すればよい。

適当なやり方。

    write(*,'(100f)') a(:)

きちんとしたやり方。以下2chより引用。

http://pc12.2ch.net/test/read.cgi/tech/1163319215/532

532 名前:デフォルトの名無しさん [sage]: 2009/03/27(金) 05:59:41  
亀だけど、Ifortなら<>がお勧め。
多次元配列の最初の数を入れることが多いです
例
program main
implicit none
integer,parameter :: num = 9
integer :: ii,jj
real :: arry(num,num)
do ii=1,num
do jj = 1,num
arry(ii,jj) = ii*jj
enddo
enddo

write(6,'(<num>F)') arry
end program 

MKL

kudpc に記載あり.

module load mkl

してから,コンパイル.お手軽.

ifort sample.f90 -mkl

概要

パッケージ名
lapack 密行列やバンド行列を直説法で解く
lapack95 密行列やバンド行列を直説法で解く
blas95 マトベク演算や内積演算を行う
sparse_blas95 疎行列のマトベク演算行う
pardiso 疎行列を直説法で解く。(条件数の大きい問題向き)
fgmres 疎行列をFlexibleGMRESで解く。

lapack

  • ifortと一緒にインストールされる.
  • 環境変数の設定をしておけばパスを通す必要はない.

ifort Version 12.0では以下のようにすれば動いた.FIXME

ifort hoge.f90 -lmkl_lapack95_lp64 -lmkl_intel_lp64 -lmkl_intel_thread -lmkl_core -liomp5 -lpthread

ver 11くらい

ifort file.f90  -lmkl -lmkl_lapack  -lmkl_em64t -lguide -lmkl_solver

lapack95

  • 線形方程式を解くパッケージ。
  • 固有値の計算や特異値分解も可能。
  • mklのlapack95はlapack90のラッパーらしい。
  • 自分でmakeする必要あり。

ライブラリの作成

  • libem64t, intel64の部分は環境に応じて適当に。オプションも適当に。デフォルトで十分そうなので、オプションはなくても良さそう。
$ cd /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/
$ sudo gnome-terminal

新しく開いた端末で作業1)

 
# . /opt/intel/Compiler/11.0/074/bin/ifortvars.sh intel64
# make libem64t 
# exit

サンプルコード 

コードのサンプルは /opt/intel/mkl/10.1.0.015/examples/lapack95/source/ にあり。ここではgesv.f90を参考にしながら説明。

コンパイルオプション(intel64)

(2010.06.22追記)最近のver.はライブラリの場所が変わったようだ.(というか今まで間違ったファイルを使ってだけかも….) Fortran90でLapack95使ったときのコンパイルコマンド.file.f90のところは適当に修正して下さい.

ifort file.f90 -L/opt/intel/Compiler/11.1/069/mkl/lib/em64t/ -I /opt/intel/Compiler/11.1/069/mkl/include/em64t/lp64/ -lmkl_lapack95_lp64 -lmkl_intel_lp64 -lmkl_intel_thread -lmkl_core -lguide -lpthread -O2

以下,古い情報

$ ifort /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/source/gesv.f90 -L/opt/intel/Compiler/11.0/074/mkl/examples/lapack95/lib/em64t/ -I /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/lib/em64t -lmkl_lapack95 -lmkl_intel_lp64 -lmkl_intel_thread -lmkl_core -lguide -lpthread
$ ./a.out < /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/data/gesv.d

コンパイルオプション(ia32)

ifort /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/source/gesv.f90 -L/opt/intel/Compiler/11.0/074/mkl/examples/lapack95/lib/32  -I /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/lib/32/ -lmkl_lapack95 -lmkl_intel -lmkl_intel_thread -lmkl_core -lguide -lpthread
$ ./a.out < /opt/intel/Compiler/11.0/074/mkl/examples/lapack95/data/gesv.d

使い方

/opt/intel/mkl/10.1.0.015/examples/lapack95/source/gesv.f90 の最初

      USE MKL95_PRECISION, ONLY: WP => SP
      USE MKL95_LAPACK, ONLY: GESV
  • 単精度はSP、倍精度はDPを使用する。
  • 呼び出すサブルーチン名をONLYの後に書く。

/opt/intel/mkl/10.1.0.015/examples/lapack95/source/gesv.f90 の中頃

      CALL GESV(  A, B )
      CALL GESV(  AA, BB(:,1), IPIV, INFO )
  • 引数の数が違うのはfortran90のoptional属性によるもの。
  • LIBRARY_PATHやINCLUDEの環境変数を追加するか,libやmodを適切な位置に動かすのが良いかも.(makeほげほげで設定できないのかしら.未確認.FIXME

blas95

  • マトベク演算やらをしてくれるパッケージ。
  • matmulよりも高速。(多分)
  • 自分でmakeする必要あり。

ライブラリの作成

  • libem64t, intel64の部分は環境に応じて適当に。オプションも適当に。デフォルトで十分そうなので、オプションはなくても良さそう。
  • ライブラリの作成方法はlapack95と同じ。
$ cd /opt/intel/Compiler/11.0/074/mkl/interfaces/blas95
$ sudo gnome-terminal
# . /opt/intel/Compiler/11.0/074/bin/ifortvars.sh intel64
# make libem64t 
# exit

サンプルコード 

コンパイルオプション

コードのサンプルは /opt/intel/Compiler/11.0/074/mkl/examples/blas95/source/ にあり。ここでは dgemmx.f90を参考にしながら説明。

$ ifort /opt/intel/Compiler/11.0/074/mkl/include/mkl_blas.f90  /opt/intel/Compiler/11.0/074/mkl/examples/blas95/source/dgemmx.f90   /opt/intel/Compiler/11.0/074/mkl/examples/blas95/source/common_func.f -lmkl_blas95 -lmkl_intel_lp64 -lmkl_sequential -lmkl_core -lpthread
$ ./a.out < /opt/intel/Compiler/11.0/074/mkl/examples/blas/data/dgemmx.d
  • /opt/intel/Compiler/11.0/074/mkl/include/mkl_blas.f90 はインターフェース
  • /opt/intel/Compiler/11.0/074/mkl/examples/blas95/source/dgemmx.f90 がメインプログラム
  • /opt/intel/Compiler/11.0/074/mkl/examples/blas95/source/common_func.f はdgemmxが使用している副プログラム(サブルーチン)

コード

/opt/intel/Compiler/11.0/074/mkl/examples/blas95/source/dgemmx.f90 のはじめのあたり。

      use mkl95_precision, only: wp => dp
      use mkl95_blas, only: gemm
  • lapack95と同様にspで単精度、dpで倍精度。
  • gemmは呼び出すルーチン名

sparse_blas95

pardiso/MKL

コンパイルオプション

  • 77でも90でもコンパイル方法は同じ。(ファイルの拡張子が異なるだけ)
  • includeする場合はパスの設定が必要.(ifortvars.*shを読み込んでいる場合は,設定済み)

intel64の場合

$ ifort hoge.f90 -lmkl_solver_lp64 -lmkl_intel_lp64 -lmkl_intel_thread -lmkl_core   -liomp5 -lpthread

ia32の場合

$ ifort hoge.f90 -lmkl_solver -lmkl_intel -lmkl_intel_thread -lmkl_core -lguide -lpthread

コメント

  • mkl_pardiso.f90をincludeせずに,mkl_pardiso.f90と一緒にコンパイルするやり方もあり。
$ifort pardiso.f90 /opt/intel/Compiler/11.0/074/mkl/include/mkl_pardiso.f90 -lmkl_solver -lmkl_intel -lmkl_intel_thread -lmkl_core -lguide -lpthread

サンプル コード

f77のコードは /opt/intel/Compiler/11.0/074/mkl/examples/solver/source/ 内にあり。

fortran90

include 'mkl_pardiso.f90'
 
program pardiso_test
  use MKL_PARDISO
  implicit none
  real(8),allocatable::a(:),b(:),x(:)
  integer::maxfct=1,mnum=1,mtype,phase=13,n,nzero,nrhs=1,iparm(64),msglvl=0,error
  type(mkl_pardiso_handle) :: pt(64)
  integer i,j
  integer,allocatable::ia(:),ja(:),perm(:)
!!! this matrix is quoted by slatec document...
!       |11 12  0  0 15|   A: 11 12 15 | 21 22 | 33 35 | 44 | 51 53 55
!       |21 22  0  0  0|  IA:  1       |  4    |  6    |  8 |  9       | 12
!       | 0  0 33  0 35|  JA:  1  2  5 |  1  2 |  3  5 |  4 |  1  3  5 
!       | 0  0  0 44  0|
!       |51  0 53  0 55|
!!! set parameter of pardiso
  pt(:)=mkl_pardiso_handle(0)
  iparm(1)=0
  mtype=11
!!! assign values to variables
  n=5
  nzero=11
  allocate(a(nzero),b(n),x(n),ia(n+1),ja(nzero),perm(n))
  ia(:)=(/1,4,6,8,9,12/)
  a(:)=(/11.d0,12.d0,15.d0,21.d0,22.d0,33.d0,35.d0,44.d0,51.d0,53.d0,55.d0/)
  ja(:)=(/1,2,5,1,2,3,5,4,1,3,5/)
!!! calculate b when x=(/1.d0,2.d0,3.d0,4.d0,5.d0/)
  b(:)=0.d0
  do i=1,5
     do j=ia(i),ia(i+1)-1
        b(i)=b(i)+a(j)*ja(j)
     end do
  end do
!!! solve linear equation by pardiso
  call pardiso(pt,maxfct,mnum,mtype,phase,n,a,ia,ja,perm,nrhs,iparm,msglvl,b,x,error)
  if(error /= 0) then 
     write(*,*) error 
     stop
  end if
  write(*,*) x
end program pardiso_test

fortran77

fortran90のサンプルを書き換え。

      program pardiso_test
      implicit none
      integer lzero,l
      parameter (lzero=11,l=5)
      real*8 a(lzero),b(l),x(l)
      integer maxfct,mnum,mtype,phase,n,nzero,nrhs,iparm(64),
     $     msglvl,error,pt(64),ia(l+1),ja(lzero),perm(l),i,j
      data ia /1,4,6,8,9,12/
      data ja /1,2,5,1,2,3,5,4,1,3,5/
      data a /11.d0,12.d0,15.d0,21.d0,22.d0,33.d0,35.d0,
     $     44.d0,51.d0,53.d0,55.d0/
ccc   this matrix is quoted by slatec document...
c     |11 12  0  0 15|   A: 11 12 15 | 21 22 | 33 35 | 44 | 51 53 55
c     |21 22  0  0  0|  IA:  1       |  4    |  6    |  8 |  9       | 12
c     | 0  0 33  0 35|  JA:  1  2  5 |  1  2 |  3  5 |  4 |  1  3  5 
c     | 0  0  0 44  0|
c     |51  0 53  0 55|
ccc   set parameter of pardiso
      do i=1,64
         pt(i)=0
      end do
      iparm(1)=0
      mtype=11
      maxfct=1
      mnum=1
      phase=13
      nrhs=1
      msglvl=0
ccc   assign values to variables
      n=5
      nzero=11
ccc   calculate b when x=(/1.d0,2.d0,3.d0,4.d0,5.d0/)
      b(:)=0.d0
      do i=1,5
         do j=ia(i),ia(i+1)-1
            b(i)=b(i)+a(j)*ja(j)
         end do
      end do
ccc   solve linear equation by pardiso
      call pardiso(pt,maxfct,mnum,mtype,phase,n,a,ia,ja,perm,nrhs,
     $     iparm,msglvl,b,x,error)
      if(error /= 0) then 
         write(*,*) error 
         stop
      end if
      write(*,*) x
      end program

fgmres

前処理を効率的に行えるようGMRESを改良したもの。前処理に反復解法が使える。

FIXME

1) sudo make libem64tとすると、「ifort: コマンドが見つかりませんでした」と怒られる。そのため、スーパーユーザー用の端末を開き、パスを通してから作業。sudoで端末を開くのは、ちょっとお行儀悪いかも。sudoに環境変数を引き継ぐやり方もありそう…
fortran/ifort.1387937552.txt.gz · 最終更新: 2017/10/03 12:55 (外部編集)