Questions on "forrtl: error (65): floating invalid" - fortran

I've been running a huge Fortran code with Intel compiler version 13.1.3.192 under the debug mode (with -O0 -g -traceback -fpe3 flags being turned on). It gave me the following output message:
... ...
forrtl: warning (402): fort: (1): In call to MPI_ALLGATHER, an array temporary was created for argument #1
forrtl: error (65): floating invalid
Image PC Routine Line Source
arts 00000000016521D9 pentadiagonal_ser 385 pentadiagonal.f90
arts 0000000001644862 pentadiagonal_ 62 pentadiagonal.f90
arts 00000000004DF167 implicit_solve_x_ 1201 implicit.f90
arts 0000000000538079 scalar_bquick_inv 383 scalar_bquick.f90
arts 00000000004EFEAC scalar_step_ 190 scalar.f90
arts 0000000000401744 simulation_run_ 182 simulation.f90
arts 0000000000401271 MAIN__ 10 main.f90
arts 0000000000400FAC Unknown Unknown Unknown
arts 000000000420E444 Unknown Unknown Unknown
arts 0000000000400E81 Unknown Unknown Unknown
and the source of the error comes from the subroutine pentadiagonal_serial, which is to solve a penta-diagonal matrix:
subroutine pentadiagonal_serial(A,B,C,D,E,R,n,lot)
use precision
implicit none
integer, intent(in) :: n,lot
real(WP), dimension(lot,n) :: A ! LOWER-2
real(WP), dimension(lot,n) :: B ! LOWER-1
real(WP), dimension(lot,n) :: C ! DIAGONAL
real(WP), dimension(lot,n) :: D ! UPPER+1
real(WP), dimension(lot,n) :: E ! UPPER+2
real(WP), dimension(lot,n) :: R ! RHS - RESULT
real(WP), dimension(lot) :: const
integer :: i
if (n .eq. 1) then
! Solve 1x1 system
R(:,1) = R(:,1)/C(:,1)
return
else if (n .eq. 2) then
! Solve 2x2 system
const(:) = B(:,2)/C(:,1)
C(:,2) = C(:,2) - D(:,1)*const(:)
R(:,2) = R(:,2) - R(:,1)*const(:)
R(:,2) = R(:,2)/C(:,2)
R(:,1) = (R(:,1) - D(:,1)*R(:,2))/C(:,1)
return
end if
! Forward elimination
do i=1,n-2
! Eliminate A(2,i+1)
const(:) = B(:,i+1)/(C(:,i)+tiny(1.0_WP))
C(:,i+1) = C(:,i+1) - D(:,i)*const(:)
D(:,i+1) = D(:,i+1) - E(:,i)*const(:)
R(:,i+1) = R(:,i+1) - R(:,i)*const(:)
in which the line
const(:) = B(:,i+1)/(C(:,i)+tiny(1.0_WP))
causes the error. I tried to print out the values of const(:) and find that there did exist Infinity values. However, I cannot understand why it can generate infinities. As far as I see, to avoid zero denominator, the tiny(1.0_WP) is added to C(:,i) and now it is nearly impossible for the denominator to be zero... I also checked when this subroutine is being called, everything is initialized or given a value after declaration. So I couldn't figure out where could go wrong.

(Answers in the comments. See Question with no answers, but issue solved in the comments (or extended in chat). There is a lot of chat in the comments and its hard to extract the actual answer, but the OP indicates it is solved. )
#SethMMorton wrote:
If any of the values of C are around -tiny then you still can end up with zero in the denominator.
Did you print out the values of C? Do small values correlate to the infinities in const?
#Alexander Vogt wrote:
Well, adding something to infinity results in a floating point exception... And I'm not sure ifort can detect that a division by infinity is zero, I guess that is another floating point exception! You'd better make sure that no infinite values occur inside C.
#Stefan wrote:
Workaround: What about the routine ?gbsv from MKL/Lapack?
Then, one last hint: Try to compile with gfortran. Different compilers create different compile-time/run-time warnings and/or errors and maybe gfortran detects your problem earlier.

Related

Fortran code produces runtime error 'operation not supported' when attempting to open a text file

I am trying to run a piece of fortran code written in f95. I have compiled it using gfortran in Ubuntu.
In the code there is a command to read in a text file. When I run it, it gives me the following error:
Fortran runtime error: Cannot open file 'input_parameters.txt': Operation not supported
This is the code up until the point that we attempt to read the text file:
program LSmodel
implicit none !this is a fortran thing that means that all variables that start with i,j,k,l,m,n are integers.
real :: sec,ran,gasdev ! random generator variables
real :: x,y,z,u,v,w,ut,vt,wt,t,dt ! simulation variables
real :: wg ! seed parametes
real :: Um,sigma_u,sigma_v,sigma_w,uw ! wind statistics variables
real :: dvaru_dz,dvarv_dz,dvarw_dz,duw_dz ! wind statistics variables
real :: dissip_m,TL ! vector over the range of ustars
real :: zs,zg,zmax ! release height & boundaries
real :: Ainv,C0inv ! inverse parameters
real :: C0,A,b,au,av,aw,dt_on_TL ! LS model parameters
real :: dz_max,dt_max ! time step limit
real :: CT,beta ! Crossing Trajectories correction
real :: C_chi,chi,TKE,T_chi,omega ! DI parameters
real :: a_ln,b_ln,sigma_chi,dissip_s ! DI parameters
real :: rhop,rho,r,g,gt,Re,AIP,Cd,nu ! IP parameters
real :: up,vp,wp,upt,vpt,wpt,vr,dt_ip,alpha ! IP parameters
real :: keepseed, maxheight
integer :: seed ! random generator variables, keepseed decides whether to keep the same seed or not for comparison of simulation
integer :: pnum, traj_exit ! simulation parameters. traj_exit counts the number of particles that have exited from the topo f the wind flow.
integer :: i,j,jj,n,ii ! counting parameters
integer :: n_ip,IP=1 ! IP parameters
character(len=80) :: filename, wgchar, foldername
real, allocatable,dimension(:) :: z_vec,Um_vec,sigma_u_vec,sigma_v_vec,sigma_w_vec,uw_vec
real, allocatable,dimension(:) :: dvaru_dz_vec,dvarv_dz_vec,dvarw_dz_vec,duw_dz_vec,dissip_m_vec
! input
open (23,file='input_parameters.txt') !opening a file for the input parameters....
read (23, *) x,C0,wg,zs,zg,beta,dt_on_TL,y,sigma_chi,C_chi,r,rhop,alpha,rho,nu, keepseed, foldername
close(23)
I am running Ubuntu 18.04.2 LTS.
An update - I have found (I believe) the reason this code was not working, although I don't know why.
The folder was in a network drive, not on my local computer. Once I moved the folder onto my local computer, I stopped getting this error.

Why can't my program print my statements?

There is 3 columns in the file i'm reading and I want to average each column and take the std. The code compiles now, but nothing is being printed.
Here is my code:
program cardata
implicit none
real, dimension(291) :: x
intEGER I,N
double precision date, odometer, fuel
real :: std=0
real :: xbar=0
open(unit=10, file="car.dat", FOrm="FORMATTED", STATUS="OLD", ACTION="READ")
read(10,*) N
do I=1,N
read(10,*) x(I)
xbar= xbar +x(I)
enddo
xbar = xbar/N
DO I =1,N
std =std +((x(I) -xbar))**2
enddo
std = SQRT((std / (N - 1)))
print*,'mean:',xbar
print*, 'std deviation:',std
close(unit=10)
end program cardata
I am fairly new to this, any input will be greatly appreciated.
Example of car.dat:
date odometer fuel
19930114 298 22.4
19930118 566 18.1
19930118 800 18.9
19930121 960 15.8
19930125 1247 19.8
19930128 1521 17.1
19930128 1817 19.8
19930202 2079 18.0
19930202 2342 10.0
19930209 2511 16.4
19930212 2780 16.7
19930214 3024 19.0
19930215 3320 17.7
19930302 3560 16.4
19930312 3853 18.8
19930313 4105 18.5
From the car.dat that you gave in the comments, it's surprising that the program doesn't show anything. When I run it, it shows a very clear runtime error:
$ gfortran -o cardata cardata.f90
$ ./cardata
At line 12 of file cardata.f90 (unit = 10, file = 'car.dat')
Fortran runtime error: Bad integer for item 1 in list input
You seem to be copying code from another example without really understanding what it does. The code, as you wrote it, expects the file car.dat to be in a certain format: First an integer, which corresponds to the number of items in the file, then a single real per line. So something like this:
5
1.2
4.1
2.2
0.4
-5.2
But with your example, the first line contains text (that is, the description of the different columns), and when it tries to parse that into an integer (N) it must fail.
I will not give you the complete example, as I have the nagging suspicion that this is some sort of homework from which you are supposed to learn something. But here are a few hints:
You can easily read several values per line:
read(10, *) date(I), odometer(I), fuel(I)
I'm assuming here that, different to your program, date, odometer, and fuel are arrays. date and odometer can be integer, but fuel must be real (or double precision, but that's not necessary for these values).
You need to jump over the first line before you can start. You can just read the line into a dummy character(len=64) variable. (I picked len=64, but you can pick any other length that you feel confident with, but it should be long enough to actually contain the whole line.)
The trickiest bit is how to get your N as it is not given at the beginning of the file. What you can do is this:
N = 0
readloop : do
read(10, fmt=*, iostat=ios) date(N+1), odometer(N+1), fuel(N+1)
if (ios /= 0) exit readloop
N = N + 1
end do readloop
Of course you need to declare INTEGER :: ios at the beginning of your program. This will try to read the values into the next position on the arrays, and if it fails (usually because it has reached the end of the file) it will just end.
Note that this again expects date, odometer, and fuel to be arrays, and moreover, to be arrays large enough to contain all values. If you can't guarantee that, I recommend reading up on allocatable arrays and how to dynamically increase their size.

How can I read data from a text file and save/write parts/variables to different text files?

I'm fairly new to Fortran so this might be a naive question. I would like to read a huge .txt file with a # of rows=540001. The data are from a sonic anemometer with measurements of velocity and temperature as u,v,w,T at five heights. Here are the first few lines of the file:
"2011-07-10 09:30:00",9838,1.132,2.30225,-0.5635,29.18585,0.30275,0.689,-0.01125,29.67004,0.2165,-0.25475,0.12725,29.8923,0.51425,3.0405,-0.58375,29.5242,-0.0085,3.6235,-0.65175,29.61972,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
"2011-07-10 09:30:00.05",9839,-0.21325,3.22775,-0.17,29.10953,0.33925,0.6867501,-0.0015,29.67874,0.1715,-0.196,0.1235,29.8923,0.035,2.6915,-0.3845,29.82806,-0.102,3.5505,-0.15825,29.61795,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
"2011-07-10 09:30:00.1",9840,0.403,3.1195,-0.37175,29.22574,0.06550001,0.6655,0.1275,29.76208,0.196,-0.2,0.1,29.901,0.16225,2.31525,-0.5975,29.69263,0.24175,3.11925,-0.3725,29.57977,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
etc...
I would like to save/write the matrices u(5,540001),v(5,540001),w(5,540001), and T(5,540001) so that I can do some calculations and plots. Here is what I am using:
PROGRAM READ_MAIZE
IMPLICIT NONE
REAL,DIMENSION(:,:),Allocatable :: u_r, v_r, w_r, T_r
CHARACTER(len=*) :: fname
fname='FINALDATA.txt'
open(unit=1,file=fname,status='old',action='read')
do i=1,540001
READ(1,*)timestamp(i),count(i),u_r(5,i),v_r(5,i),w_r(5,i), &
T_r(5,i),u_r(2,i),v_r(2,i),w_r(2,i),T_r(2,i), &
u_r(1,i),v_r(1,i),w_r(1,i),T_r(1,i), &
u_r(3,i),v_r(3,i),w_r(3,i),T_r(3,i), &
u_r(4,i),v_r(4,i),w_r(4,i),T_r(4,i),flags(1:20)
end do
close(1)
WRITE(U_maize,'(A,I7.7,A,I7.7,A)'), &
'.txt'
open(11,file=U_maize,status='unknown',action='write')
write(11,'(F20.14)')(u_r)
end
Never mind the order in u_r(5,i) followed by u_r(2,i)... (they just correspond to different heights that are out of order). This is not working.
There's quite a lot going on in your code which makes it hard to understand what you're trying to do in the first place. I have annotated your code below and turned it into something that compiles and produces output. Maybe it'll help.
PROGRAM READ_MAIZE
IMPLICIT NONE ! This means that every variable has to be declared
! explicitly. You don't do that. So I did it for you
REAL,DIMENSION(:,:),Allocatable :: u_r, v_r, w_r, T_r
integer, dimension(:), allocatable :: data_count ! using fortran keywords
! (such as "count") as variables is dangerous and should be avoided
character(len=len("2011-07-10 09:30:00.05")), allocatable :: timestamp(:)
CHARACTER(len=*), parameter :: fname='FINALDATA.txt'
character(len=len("U_XXXXXXX_XXXXXXX.txt")) :: U_maize
integer :: in_unit, out_unit ! Use integer variables for the unit.
! together with newunit keyword, this is
! safer
integer, parameter :: num_records = 3 ! you need to up this number to
! 540001 again
integer :: i
! If you have allocatable arrays, you need to allocate them before you
! can use them
allocate(u_r(5, num_records))
allocate(v_r(5, num_records))
allocate(w_r(5, num_records))
allocate(T_r(5, num_records))
allocate(data_count(num_records))
allocate(timestamp(num_records))
! the "newunit" keyword is a safe way to create a unique unit
! identifier. You should really use this.
open(newunit=in_unit,file=fname,status='old',action='read')
do i=1,num_records
READ(in_unit,*) timestamp(i), data_count(i), &
u_r(5,i),v_r(5,i),w_r(5,i),T_r(5,i), &
u_r(2,i),v_r(2,i),w_r(2,i),T_r(2,i), &
u_r(1,i),v_r(1,i),w_r(1,i),T_r(1,i), &
u_r(3,i),v_r(3,i),w_r(3,i),T_r(3,i), &
u_r(4,i),v_r(4,i),w_r(4,i),T_r(4,i) ! I left out the flags
! since I didn't know what
! that was.
end do
close(in_unit)
! I don't know how the file name should be constructed, except
! that it should end in a .txt, and the format. So I made something up.
write(U_maize, '(A, I7.7, A, I7.7, A)') 'U_', 35, '_', 6, '.txt'
open(newunit=out_unit,file=U_maize,status='unknown',action='write')
! To make it more readable, I tell write to write 5 numbers per row,
! Not sure whether this is what you want.
write(out_unit,'(5(X, F20.14))') u_r
close(out_unit) ! I know it isn't technically needed, but please always
! close files when finished, even if the program terminates anyway.
end program READ_MAIZE ! tell the compiler what you want to end here.

Cannot run Fortran code

My program runs with errors and I really have no idea why, will you help me please? The question is as below:
The flow problem is classic example of viscous diffusion. The governing equation for such problem was derived using boundary layer theory to reduce the full Navier- Stokes equations to the single parabolic PDE.
with the necessary initial and boundary conditions,
t = 0: u(0) = 0, u(0.04m) = 0;
t > 0: u(0) = 40.0, u(0.04m) = U = 0.0m/s.
This problem may be described physically as transient viscous-driven flow between two plates of infinite extent and separated by a distance of 0.04m. Initially both plates are at rest. After time,t=0, the upper plate is set in motion in the positive x-direction with a velocity of 40.0m/s. Due to the viscosity of the fluid filling the space between the plates, successive lamina of fluid are set in motion as time elapses. Eventually, the system reaches a “quasi-steady state”, as the velocity profile becomes more or less constant in time. The governing equation lends nicely to the use of finite difference techniques to solve the problem in the transient domain.
Computer Code in Fortran for DUFORT FRANKEL SCHEME.
! Homework1 DUFORT FRANKE SCHEME
! Program computes the numerical solution to the
! Transient Flow Problem.
! The following initial and bounadry conditions are applied:
! t=0: u(y=0)=40.0m/s
! t>0: u(y=0)=0.0; u(y=0.04m)=0.0
parameter(maxn=30,eps=1.0e-3)
integer k,m,mm,count
real*8 u_old(1001,maxn),u_new(1001,maxn),y(maxn)
real*8 t,tau,h,r,tmax,u_init,nu,sum,error
!
data h,m,u_init,nu,r,tmax /0.001,41,0.0,2.17e-4,0.217,2.5e5/
!
open(unit=1,file='hw1_dufort.out',status='unknown')
tau=r*h**2/nu
mm=m-1
error=1.0
!
count=0
k=1
t=0.0
y(1)=0.0
!
do 2 i=2,m
y(i)=y(i-1)+h
2 continue
!
write(1,*)'Velocity Results:'
write(1,10)t,(u_old(k,j),j=1,m)
do while ((error.gt.eps).and.(count.lt.1080))
count=count+1
sum=0.0
t=t+tau
u_old(k,1)=40.0
u_old(k,m)=0.0
do 4 i=2,mm
if (k.lt.2) then
u_new(k,i)=(2.0*r/(1.0+2.0*r))*(u_old(k,i+1)+u_old(k,i-1))
else
u_new(k,i)=(2.0*r/(1.0+2.0*r))*(u_old(k,i+1)+u_old(k,i-1))+ ((1.0 -
& 2.0*r)/(1.0+2.0*r))*u_old(k-1,i)
end if
end do
!
10 format(2x,f10.3,2x,41f8.4)
write(1,'(" Number of steps for convergence = ",i4)')count
end

Error: Two main PROGRAMs at (1) and (2)

I'm using the Simply Fortran compiler and when I try to compile I get the error:
prog.f95:35.13:
1 Implicit None
prog.f95:53.65:
2 open (unit=1,file='in',status='OLD') ! opens file with parameters
Error: Two main PROGRAMs at (1) and (2)
I have included only the parts of the code in which the errors occur since the whole thing is quite long. This begins at the very beginning of the program. Let me know if I should include more.
Implicit None
Integer :: i,j,iter
real(8) :: Elow,Ehigh,chi,B_NS,Vbrprof,Neprof,taues
real(8) :: Xcyclave,a
character(8) systemdate
character(10) systemtime
character(5) timezone
integer dateandtime(8)
character(8) systemdate2
character(10) systemtime2
character(5) timezone2
integer dateandtime2(8)
character(len=40) :: infname,outfname,comm
include 'common.f95'
open (unit=1,file='in',status='OLD') ! opens file with parameters
read (1,1) ! comment line
read (1,1) outfname
read (1,*) Elow,Ehigh ! lower and higher energy
read (1,*) Eminf,Emind,Emaxf ! min and max energy for fedd
read (1,*) Rin, Rout ! inner and outer radii
read (1,*) profpar(1) ! for Ne
read (1,*) profpar(2) ! Te in keV
read (1,*) profpar(3) ! for absorption+emission
read (1,*) profpar(4) ! T_bb for neutron star in keV
read (1,*) profpar(5) ! for bulk velocity
read (1,*) profpar(6) ! other parameter for model
read (1,*) profpar(10) ! magnetic moment in 10^27 CGS
1 format (A10)
close (1)
The compiler is probably seeing an END xxx statement in the file common.f95. The file common.f95 is possibly not meant to be used as an INCLUDE file - it may be a program unit in its own right.