diff --git a/example_packages/preprocess_project_root/app/main.f90 b/example_packages/preprocess_project_root/app/main.f90 new file mode 100644 index 0000000000..9a6b485944 --- /dev/null +++ b/example_packages/preprocess_project_root/app/main.f90 @@ -0,0 +1,18 @@ +!> from https://stackoverflow.com/a/46342008 +#ifdef __GFORTRAN__ +# define STRINGIFY_START(X) "& +# define STRINGIFY_END(X) &X" +#else /* default stringification */ +# define STRINGIFY_(X) #X +# define STRINGIFY_START(X) & +# define STRINGIFY_END(X) STRINGIFY_(X) +#endif + +program preprocess_project_root + implicit none + character(len=*), parameter :: root = STRINGIFY_START(PROJECT_ROOT) + STRINGIFY_END(PROJECT_ROOT) + + print *, root + +end program preprocess_project_root diff --git a/example_packages/preprocess_project_root/fpm.toml b/example_packages/preprocess_project_root/fpm.toml new file mode 100644 index 0000000000..a98ebc44ec --- /dev/null +++ b/example_packages/preprocess_project_root/fpm.toml @@ -0,0 +1,4 @@ +name = "preprocess_project_root" + +[preprocess] +[preprocess.cpp] diff --git a/example_packages/preprocess_project_root/readme.md b/example_packages/preprocess_project_root/readme.md new file mode 100644 index 0000000000..86cac4f497 --- /dev/null +++ b/example_packages/preprocess_project_root/readme.md @@ -0,0 +1,11 @@ +# Preprocess_project_root +If you have activated preprocess option in `fpm.toml` via +```toml +[preprocess] +[preprocess.cpp] +``` +some predefined variables will be added to macro definitions. In this example, the macro `PROJECT_ROOT=\path\to\project` is passed to the Fortran source code. + +In practice, the value of `PROJECT_ROOT`, which is literally `\path\to\project`, is simply pasted without quoted as a valid string literal. So the code using `PROJECT_ROOT` macro may not compile. You can refer to [Stringify macro with GNU gfortran](https://stackoverflow.com/a/46342008) to solve this problem. + + diff --git a/src/fpm_compiler.f90 b/src/fpm_compiler.f90 index 5f655ac1ed..c0d3c994c5 100644 --- a/src/fpm_compiler.f90 +++ b/src/fpm_compiler.f90 @@ -42,6 +42,7 @@ module fpm_compiler & getline, run use fpm_strings, only: split, string_cat, string_t, str_ends_with, str_begins_with_str use fpm_manifest, only : package_config_t +use fpm_os, only: get_current_directory use fpm_error, only: error_t implicit none public :: compiler_t, new_compiler, archiver_t, new_archiver, get_macros @@ -485,6 +486,23 @@ function get_macros(id, macros_list, version) result(macros) end do + !> add predefined variables + call set_predefined_macro() + +contains + + !> append predefined variable as macro definition + subroutine set_predefined_macro() + type(error_t), allocatable :: error + character(len=:), allocatable :: project_root + + !> add PROJECT_ROOT + call get_current_directory(project_root, error) + if (.not. allocated(project_root)) project_root = '' + macros = macros//' '//macro_definition_symbol//"PROJECT_ROOT="//project_root + + end subroutine set_predefined_macro + end function get_macros function get_include_flag(self, path) result(flags)