Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Change of directory in Fortran in a non compiler-specific way

I wish to change the working directory in a Fortran 90 code. Is it possible to do this in a non compiler-specific way? Here is my code:

program change_directory
    integer :: ierr

    call system("mkdir -p myfolder/")
    !call system("cd myfolder/")   !doesn't work
    ierr = chdir("myfolder")
    if (ierr.NE.0) then
        write(*,'(A)') "warning: change of directory unsuccessful"
    end if

    open(unit=33,file="myfile.txt",iostat=ierr)
    if (ierr.EQ.0) then
        write(unit=33,fmt='(A)') "Test message"
        close(unit=33)
    end if
end program change_directory

Clearly, using cd myfolder/ in a system call doesn't work. The Intel reference says I need to add 'use ifport'. There's no such mention in the GCC reference, though. Leaving out 'use ifport', I can compile the above code under ifort without any trouble. When I put it in, however, it won't compile with gcc (because gcc doesn't have the ifport module)--and not only that, it won't compile under Intel Fortran either--I'm getting the following error:

$ ifort change_dir.f90 -o change_dir
change_dir.f90(5): error #6552: The CALL statement is invoking a function subprogram as a subroutine.   [SYSTEM]
    call system("mkdir -p myfolder/")
---------^
compilation aborted for change_dir.f90 (code 1)

So my question is the following: is there a better way to do this? I'd like to keep my code as compiler-independent as possible. At the moment, I primary use gfortran/ifort and mpif90/mpiifort.

like image 251
nathanielng Avatar asked Nov 01 '22 14:11

nathanielng


1 Answers

See also Is there any way to change directory using C language? . You can make your own interface to the chdir() POSIX call to be independent of the Intel's interface. On Windows it is similar.

module chdir_mod

  implicit none

  interface
    integer function c_chdir(path) bind(C,name="chdir")
      use iso_c_binding
      character(kind=c_char) :: path(*)
    end function
  end interface

contains

  subroutine chdir(path, err)
    use iso_c_binding
    character(*) :: path
    integer, optional, intent(out) :: err
    integer :: loc_err

    loc_err =  c_chdir(path//c_null_char)

    if (present(err)) err = loc_err
  end subroutine
end module chdir_mod


program test

  use chdir_mod

  call chdir("/")

  call system("ls -l")

end

and when run

> gfortran chdir.f90 
> ./a.out 
celkem 120
drwxr-xr-x   2 root root  4096 15. říj 14.42 bin
drwxr-xr-x   5 root root  4096 15. říj 14.43 boot
...

On ifort it works too as it does on sunf90.

(Note: this relies on default character being the same as c_char. That is quite a safe assumption. If it is not the case the compiler will complain and a conversion has to be made.)

like image 94
Vladimir F Героям слава Avatar answered Nov 13 '22 02:11

Vladimir F Героям слава