Search code examples
fortranfortran-common-block

Value not passing to subroutine using a common block


I'm trying to pass a parameter between a Fortran main program and a subroutine. However for some reason a different value is obtained in the subroutine. I am using common blocks.

program main
nzcur=1
write(*.*)"nzcur in main",nzcur

call hit

subroutine hit
common/part/nzcur
write(*,*)"nzcur in hit",nzcur; pause
end

end program

I would expect nzcur=1 but I get nzcur=0.

I think it could be a data type mismatch as I do not define it, only as a common block.


Solution

  • As noted in the comments, the correct learning response to this question is to avoid using common blocks to have access to variables from other scopes. In writing code in the modern era there are far better ways (more later).

    Fortunately, however, we can look at this question in terms of "how do I understand what is happening with this common block?". Such a question is useful to those unfortunate programmers trying to understand old (or badly written new) code.

    In considering the program of the question one should note that several corrections are required to have compilable code (with different possible approaches). The errors there are not directly relevant to the discussion.

    In the subroutine

    subroutine hit
    common/part/nzcur
    write(*,*)"nzcur in hit",nzcur; pause
    end
    

    we have a named common block called part, with one numeric storage unit which contains the integer variable nzcur (thanks to implicit typing).

    In the question there is clearly the expectation that the variable nzcur in this common block accesses some other variable called nzcur and that this other variable is the one in the main program called nzcur. This is not correct.

    nzcur in the subroutine is associated only with the first numeric storage unit of any other common block named part. The association is not based on named or location in the common block definition.

    In the program of the question, there is no other common block called part; nzcur of the subroutine is not associated with anything else. It is certainly not associated with a variable not in a common block.

    Because of this lack of association, the variable is not defined by the time the write statement references it. Again, the definition of the variable in the main program does not affect the definition of the local variable in the subroutine.

    To "correct" the association, it will be necessary to put the variable nzcur of the main program in the correct location in a common block named part (in the main program).


    To answer the question of "how do I set the value of nzcur in the subroutine without using common blocks?", refer to other questions such as this one.