[comment {-*- flibs -*- doctools manpage}]
[manpage_begin flibs/m_platform n 1.0]
[copyright {2008 Arjen Markus <arjenmarkus@sourceforge.net>}]
[copyright {2008 Michael Baudin <michael.baudin@gmail.com>}]
[moddesc flibs]
[titledesc {Platform-dependent routines and features}]

[description]

The [strong m_platform] module contains parameters to identify the
platform the program is running on and provides 
several routines to interact with the operating system.

[section OVERVIEW]

The goal is to make the client source code as independent as possible
from the particular environment, that is 
[list_begin bullet]
[bullet] independent from the operating system, so that the 
binaries can be used under Windows, Linux or any other
specific OS without modifying the source code,
[bullet] independent from the fortran compiler, so that the 
binaries can be generated with gfortran Intel Fortran, Absoft,
or any other specific compiler without modifying the source code.
[list_end]

For instance, the [strong m_platform] module provides the 
following features :
[list_begin bullet]
[bullet]
The parameter PLATFORM_OS identifies the operating system and the
parameter PLATFORM_PLATFORM identifies the general category.
[bullet]
The subroutine platform_system() hides the platform-specific details of
running an external command or program.
[list_end]

The function platform_get_os() returns an integer which identifies
the operating system and the function platform_get_platform() identifies
the general category.
For example, the file separator is different on windows ("\"),
unix ("/") and Mac (":"). In the following example, extracted from the
m_vfile module included with flibs, the platform_get_platform()
function is used to configure the separator for the current platform.

[example {
     use m_platform, only : &
       platform_get_platform , &
       PLATFORM_PLATFORM_WINDOWS ,&
       PLATFORM_PLATFORM_UNIX , &
       PLATFORM_PLATFORM_MAC
     integer :: platform
     character (len=1) :: VFILE_PLATFORM_SEPARATOR
     platform = platform_get_platform ()
     select case ( platform )
     case ( PLATFORM_PLATFORM_WINDOWS )
       VFILE_PLATFORM_SEPARATOR = VFILE_PLATFORM_SEPARATOR_WINDOWS
     case ( PLATFORM_PLATFORM_UNIX )
       VFILE_PLATFORM_SEPARATOR = VFILE_PLATFORM_SEPARATOR_UNIX
     case ( PLATFORM_PLATFORM_MAC )
       VFILE_PLATFORM_SEPARATOR = VFILE_PLATFORM_SEPARATOR_MAC
     case default
       print *, "I come from Vega."
       return
     end select
}]

   The subroutine platform_system() allows to execute an external program at the 
   system level. This routine is generally provided by the fortran compiler as an
   extension to standard fortran. But some compilers provide the feature
   as a subroutine (for example gfortran), while other compilers provide the 
   feature as a function (for example Intel Fortran). In the following example,
   one execute a Monte-Carlo simulation with no dependency on the specific 
   compiler.
 
[example {
      use m_platform, only platform_system
      call platform_system ( "montecarlo.exe" , status )
}]

[para]
This is a sketch of available routines :
[list_begin bullet]
[bullet] platform_system                       Executes an external command on the system
[bullet] platform_get_os                       Returns the current operating system
[bullet] platform_get_platform                 Returns the current platform
[bullet] platform_get_environment_variable     Get to one environment variable
[bullet] platform_cd                           Change the system current directory
[bullet] platform_stat                         Get status of a file
[list_end]

[subsection "Pre-processing macros"]

The source code of m_platform is based on pre-processing macro,
which must be configured for the specific couple (OS,compiler) at use.
With most compilers, defining a pre-processing macro simply
consists in enabling the pre-processing with a specific
option and adding "-D<macro>" options on the command-line.

[para]
The only mandatory pre-processing macro which must be defined is
the _PLATFORM_OS_<your OS> macro.
Optionnaly, other pre-processing macros may be defined so that
the client code may access to additionnal features.
If a feature is used and the associated macros have not
been defined, the "status" integer of the associated routine
will have the value PLATFORM_ERROR_UNDEFINED_SERVICE.

[subsection "Compile"]
The "make" directory provided with flibs should help the 
use to compile m_platform. The "make/makefile" contains all the 
makefiles necessary for the project, include specific settings
for several compilers. the "make/visualstudio" directory include 
all projects .nfproj and solutions .sln files necessary to 
compile the project with Intel Fortran 8 and Visual Studio 2003.

[subsection "Operating System dependency"]

The m_platform module [strong must] be informed of the specific OS for which
it is compiled. One of the following pre-processing macros [strong must] be
defined to set the spefic OS at use :
[list_begin bullet]
[bullet] _PLATFORM_OS_WINDOWS_95
[bullet] _PLATFORM_OS_WINDOWS_NT 
[bullet] _PLATFORM_OS_MAC 
[bullet] _PLATFORM_OS_SUN 
[bullet] _PLATFORM_OS_LINUX 
[bullet] _PLATFORM_OS_UNIX
[list_end]

[subsection "System fortran extension"]

The SYSTEM fortran extension allows to execute an external program.
Depending on the compiler, the SYSTEM fortran extension is provided
as a subroutine or a function. The m_platform module [strong may] be informed
of the particular version of the SYSTEM extension at use and one
of the following pre-processing macro must be defined :
[list_begin bullet]
[bullet] _PLATFORM_SYSTEM_SUBROUTINE
[bullet] _PLATFORM_SYSTEM_FUNCTION
[list_end]
 See in your compiler manual for the specific settings.
 For example, this is a short list of compilers and the
 SYSTEM provided :
[list_begin bullet]
[bullet] function : Intel Fortran, g95.
[bullet] subroutine : gfortran,
[list_end]

 [subsection "Environment variables extension"]

 The fortran 2003 standard introduces a standard way of accessing
 to the environment variables. Older compilers does not match
 that standard but provide extensions to access to environment variables.
 To inform the m_platform module of the particular environment
 variable extension, one of the following pre-processing macro [strong may]
 be defined :
 [list_begin bullet]
[bullet] _PLATFORM_INTEL_FORTRAN_PORTABILITY_ROUTINES
[bullet] _PLATFORM_FORTRAN_2003
[list_end]

[subsection "Change directory fortran extension"]
Depending on the compiler, the "CHDIR" fortran extension is provided
as a subroutine or a function.
To inform the m_platform module of the particular CHDIR extension,
one of the following pre-processing macro [strong may] be defined :
[list_begin bullet]
[bullet] _PLATFORM_CHDIR_SUBROUTINE
[bullet] _PLATFORM_CHDIR_FUNCTION
[list_end]
See in your manual for the specific settings.
For example, this is a short list of compilers and their particular
CHDIR provided :
[list_begin bullet]
[bullet] function : Intel Fortran, g95, gfortran
[bullet] subroutine : gfortran
[list_end]

[subsection "File stat fortran extension"]
Depending on the compiler, the "STAT" fortran extension is
provided as a subroutine or a function.
For example, this is a short list of compilers and their particular
STAT provided :
[list_begin bullet]
[bullet] function : Intel Fortran, g95
[bullet] subroutine : gfortran
[list_end]
To inform the m_platform module of the particular STAT extension,
one of the following pre-processing macro [strong may] be defined :
[list_begin bullet]
[bullet] _PLATFORM_STAT_SUBROUTINE
[bullet] _PLATFORM_STAT_FUNCTION
[list_end]

[subsection "Example of compiler settings"]
 This is an abstract of all pre-processing macros for several compilers.

[para]
Compiler : [emph gfortran]
[list_begin bullet]
[bullet] _PLATFORM_FORTRAN_2003
[bullet] _PLATFORM_CHDIR_SUBROUTINE
[bullet] _PLATFORM_STAT_SUBROUTINE
[bullet] _PLATFORM_SYSTEM_SUBROUTINE
[list_end]

[para]
Compiler : [emph "Intel Fortran"]
[list_begin bullet]
[bullet] _PLATFORM_INTEL_FORTRAN_PORTABILITY_ROUTINES
[bullet] _PLATFORM_CHDIR_FUNCTION
[bullet] _PLATFORM_STAT_FUNCTION
[bullet] _PLATFORM_SYSTEM_FUNCTION
[list_end]

[para]
Compiler : [emph g95]
[list_begin bullet]
[bullet] _PLATFORM_FORTRAN_2003
[bullet] _PLATFORM_CHDIR_FUNCTION
[bullet] _PLATFORM_STAT_FUNCTION
[bullet] _PLATFORM_SYSTEM_FUNCTION
[list_end]

[section ROUTINES]
The module contains the following routines.

[list_begin definitions]

[call [cmd "use m_platform"]]
To import the subroutines, use this module.

[call [cmd "platform_system"] ([arg command] [opt ", status"])]
[list_begin arg]
[arg_def [type "character(len=*) ::"] command]
[arg_def [type "integer, intent ( out ), optional ::"] status]
[list_end]
Run an external command or program, optionally retrieving the status of
that command. Under Windows the "call system" may generate the display of a console.
Optional argument [arg status] contains the execution status. 
Notice that the information contained
in it is not very reliable - some systems do not give any information.
The [arg command] to run is quite likely platform-dependent.

[call [cmd "platform_get_os()"] result ( currentos )]
[list_begin arg]
[arg_def [type "integer ::"] currentos]
[list_end]
Return the type of operating system, one of:
PLATFORM_OS_WINDOWS_95, PLATFORM_OS_WINDOWS_NT,
PLATFORM_OS_MACOS, PLATFORM_OS_SUNOS, PLATFORM_OS_LINUX,
PLATFORM_OS_UNIX.
The actual integer value should not be used directly ; instead, it
should be compared against the PLATFORM_OS_* public variables.


[call [cmd "platform_osstring"] ([arg currentos])]
[list_begin arg]
[arg_def [type "character(len=*), intent(out) ::"] currentos]
[list_end]
Returns a string containing the current operating system running on the current machine,
one of "Windows 95", "Windows NT", "MacOS", "SunOS", 
"Linux" or "Unix".



[call [cmd "platform_get_platform()"]  result ( currentplatform )]
[list_begin arg]
[arg_def [type "integer ::"] currentplatform]
[list_end]
Return the category of platform, one of:
PLATFORM_PLATFORM_WINDOWS, PLATFORM_PLATFORM_MAC, PLATFORM_PLATFORM_UNIX
The actual integer value should not be used directly ; instead, it
should be compared against the PLATFORM_PLATFORM_* public variables.

[call [cmd "platform_platformstring"] ([arg currentplatform])]
[list_begin arg]
[arg_def [type "character(len=*), intent(out) ::"] currentplatform]
[list_end]
Returns a string containing the current platform running on the current machine,
one of "Windows", "Mac", "Unix".



[call [cmd "platform_get_environment_variable"] ( [arg envvar] [arg ", value"])]
[list_begin arg]
[arg_def [type "character(len=*) ::"] envvar]
[arg_def [type "character(len=*) ::"] value]
[list_end]
Retrieve the value of the environment variable [arg envvar]. There is no indication of
whether the variable indeed exists and it is up to the calling program
to provide a string argument sufficiently long to hold the value.
The environment variable [arg envvar] is case-sensitive on
some platforms, case-insensitive on others. This is entirely up to the
platform.
As the underlying routines give no indication of the existence 
of the environment variable, it is probably best to
fill the [arg value] with a known value first (like: "????") 
to check it.


[call [cmd "platform_cd"] ( [arg dirname] [opt ", status"])]
[list_begin arg]
[arg_def [type "character(len=*), intent(in) ::"] dirname]
[arg_def [type "integer, intent(out) , optional ::"] status]
[list_end]
Change working directory to [arg dirname]. 
If [arg status] is supplied, it contains 0 on success or nonzero error code
upon return


[call [cmd "platform_stat"] ( [arg filename] [arg ", statarray"] [opt ", status"])]
[list_begin arg]
[arg_def [type "character(len=*), intent(in) ::"] filename]
[arg_def [type "integer, dimension (1:13) , intent(out)  ::"] filename]
[arg_def [type "integer, intent(out) , optional ::"] status]
[list_end]
Get status of the file [arg filename] and fills the array [arg statarray]
with the following content.
[list_begin bullet]
[bullet] statarray(1) Device ID
[bullet] statarray(2) Inode number
[bullet] statarray(3) File mode
[bullet] statarray(4) Number of links
[bullet] statarray(5) Owner's uid
[bullet] statarray(6) Owner's gid
[bullet] statarray(7) ID of device containing directory entry for file (0 if not available)
[bullet] statarray(8) File size (bytes)
[bullet] statarray(9) Last access time
[bullet] statarray(10) Last modification time
[bullet] statarray(11) Last file status change time
[bullet] statarray(12) Preferred I/O block size (-1 if not available)
[bullet] statarray(13) Number of blocks allocated (-1 if not available)
[list_end]
If [arg status] is supplied, it contains 0 on success or nonzero error code
upon return


[list_end]



[manpage_end]
