IAP GITLAB

Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found

Target

Select target project
  • AirShowerPhysics/corsika
  • rulrich/corsika
  • AAAlvesJr/corsika
  • Andre/corsika
  • arrabito/corsika
  • Nikos/corsika
  • olheiser73/corsika
  • AirShowerPhysics/papers/corsika
  • pranav/corsika
9 results
Show changes
Commits on Source (2152)
Showing
with 594 additions and 1576 deletions
*.inl gitlab-language=c++
\ No newline at end of file
......@@ -2,9 +2,23 @@
**/*~
**/*.bak
build/
install/
.vscode/
Framework/Particles/GeneratedParticleProperties.inc
flymd.html
flymd.md
Testing
tags
Environment/GeneratedMediaProperties.inc
CMakeUserPresets.json
corsika/framework/core/GeneratedParticleClasses.inc
corsika/framework/core/GeneratedParticleProperties.inc
corsika/framework/core/particle_db.pkl
corsika/media/GeneratedMediaProperties.inc
corsika/modules/epos/Generated.inc
corsika/modules/fluka/Generated.inc
corsika/modules/qgsjetII/Generated.inc
corsika/modules/sibyll/Generated.inc
corsika/modules/sophia/Generated.inc
conan_cmake/
corsika-cmake.sh
This diff is collapsed.
Issues: Closes #....
The code approval procedure is described in the wiki: [Code approval procedure wiki](https://gitlab.ikp.kit.edu/AirShowerPhysics/corsika/-/wikis/Code-Approval-Procedure)
The code approval procedure is described in the wiki: [Code approval procedure wiki](https://gitlab.iap.kit.edu/AirShowerPhysics/corsika/-/wikis/Code-Approval-Procedure)
- [ ] The MR is without `WIP/Draft` status
- [ ] Make sure the most recent CI jobs (config, quality, build_test_example) all run fine with no failures
- if "check clang-format" failed: the code contributor has to run `./do-clang-format.py --apply` eventually with the `--all` option
- if "check copyright" failed the code contributor has to run`./do-copyright.py --add=20xy`
- [ ] Make sure also the jobs with MR-label `ready for code review` succeed. This includes the optional jobs, in particular 'coverage', 'release-clang-8", "release-u-18.04" and make sure no problems occur. You may have to trigger a pipeline manually to check this.
- [ ] Make sure also the jobs with MR-label `ready for code review` succeed. This includes the optional jobs, in particular 'coverage', 'release-full-clang-14", "release-full-u-22_04" and make sure no problems occur. You may have to trigger a pipeline manually to check this.
- [ ] Check in the "coverage" job output that the coverage did not decrease. It should always stay, or increase. If it decreased --> ask contributor to add further needed unit tests, and check coverage report.
- On the MR page, open the "Open in Web IDE" tool
- [ ] Check if the provided solution solves the Issue, discuss on gitlab
......
[submodule "modules/data"]
path = modules/data
url = ../../AirShowerPhysics/corsika-data
branch = master
shallow = true
[submodule "externals/spdlog"]
path = externals/spdlog
url = https://github.com/gabime/spdlog.git
shallow = true
[submodule "modules/proposal"]
path = modules/proposal
url = https://github.com/tudo-astroparticlephysics/PROPOSAL.git
branch = restructure_parametrization
shallow = true
path = modules/data
url = ../../AirShowerPhysics/corsika-data.git
branch = master
shallow = true
[submodule "modules/conex"]
path = modules/conex
url = ../../AirShowerPhysics/cxroot
path = modules/conex/cxroot
url = ../../AirShowerPhysics/cxroot.git
branch = master
shallow = true
shallow = true
* milestone1 release: So 7. Okt 15:51:07 CEST 2018
cmake_minimum_required (VERSION 3.9)
#
#+++++++++++++++++++++++++++++
# prevent in-source builds and give warning message
# (c) Copyright 2018 CORSIKA Project, corsika-project@lists.kit.edu
#
if ("${CMAKE_BINARY_DIR}" STREQUAL "${CMAKE_SOURCE_DIR}")
message (FATAL_ERROR "In-source builds are disabled.
Please create a build-dir and use `cmake <source-dir>` inside it.
NOTE: cmake will now create CMakeCache.txt and CMakeFiles/*.
You must delete them, or cmake will refuse to work.")
endif ()
# See file AUTHORS for a list of contributors.
#
# This software is distributed under the terms of the 3-clause BSD license.
# See file LICENSE for a full version of the license.
#
cmake_minimum_required (VERSION 3.9)
#+++++++++++++++++++++++++++++
# project name
# version is: "8.major.minor.patch"
# major: API changes
# minor: no API changes
# patch: bug fix and small improvements
#
set (c8_version 8.0.0.0)
project (
corsika
VERSION 8.0.0
VERSION ${c8_version}
DESCRIPTION "CORSIKA C++ project (alpha status)"
LANGUAGES CXX
)
#+++++++++++++++++++++++++++++
# for pre-defined standard path
#
include (GNUInstallDirs)
#+++++++++++++++++++++++++++++
# as long as there still are modules using it:
# prevent in-source builds and give warning message
#
enable_language (Fortran)
set (CMAKE_Fortran_FLAGS "-std=legacy -Wfunction-elimination")
if ("${CMAKE_BINARY_DIR}" STREQUAL "${CMAKE_SOURCE_DIR}")
message (FATAL_ERROR "In-source builds are disabled.
Please create a build-dir and use `cmake <source-dir>` inside it.
NOTE: cmake will now create CMakeCache.txt and CMakeFiles/*.
You must delete them, or cmake will refuse to work.")
endif ()
#++++++++++++++++++++++++++++
# cmake version-specific settings
#
# https://cmake.org/cmake/help/latest/policy/CMP0079.html
if (POLICY CMP0079)
cmake_policy (SET CMP0079 NEW)
endif ()
# Download timestamp for external modules
if (POLICY CMP0135)
cmake_policy (SET CMP0135 OLD)
endif ()
# AUtomatically add extensions to filenames if needed (old behaviour)
if (POLICY CMP0115)
cmake_policy (SET CMP0115 OLD)
endif ()
#+++++++++++++++++++++++++++++
# warn user if system is not UNIX
#
if (NOT UNIX)
message (FATAL_ERROR "| CORSIKA8 > This is an unsupported system.")
endif ()
#
#+++++++++++++++++++++++++++++
# cmake path dir, and cmake config
#
set (CORSIKA8_CMAKE_DIR "${PROJECT_SOURCE_DIR}/cmake")
set (CMAKE_MODULE_PATH "${CORSIKA8_CMAKE_DIR}" ${CMAKE_MODULE_PATH})
include (CorsikaUtilities) # extra cmake function
set (CMAKE_MODULE_PATH "${CORSIKA8_CMAKE_DIR}" ${CMAKE_MODULE_PATH})
if(DEFINED CONAN_CMAKE_DIR)
list(APPEND CMAKE_MODULE_PATH "${CONAN_CMAKE_DIR}")
endif(DEFINED CONAN_CMAKE_DIR)
set (CMAKE_VERBOSE_MAKEFILE OFF) # this can be done with `make VERBOSE=1`
# ignore many irrelevant Up-to-date messages during install
set (CMAKE_INSTALL_MESSAGE LAZY)
#+++++++++++++++++++++++++++++
# Extra cmake functions for registering and running tests
#
include (corsikaUtilities) # extra cmake functions
#+++++++++++++++++++++++++++++
# Setup hardware and infrastructure dependent defines, and general settings
#
include (corsikaDefines)
#+++++++++++++++++++++++++++++
# check if compiler is C++17 compliant
#
include (CheckCXXCompilerFlag)
check_CXX_compiler_flag ("--std=c++17" COMPILER_SUPPORTS_CXX17)
check_CXX_compiler_flag ("-std=c++17" COMPILER_SUPPORTS_CXX17)
if (NOT COMPILER_SUPPORTS_CXX17)
message (FATAL "| CORSIKA8 > The compiler ${CMAKE_CXX_COMPILER} has no C++17 support. Please use a different C++ compiler.")
endif ()
# set CXX compile flags and options and warning settings
set (CMAKE_CXX_STANDARD 17)
set (CMAKE_CXX_EXTENSIONS OFF)
#
#+++++++++++++++++++++++++++++
# Compiler and linker flags, settings
#
......@@ -63,90 +107,110 @@ set (CMAKE_CXX_EXTENSIONS OFF)
# FYI: optimizer flags: -O2 would not trade speed for size, neither O2/3 use fast-math
# debug: O0, relwithdebinfo: 02, release: O3, minsizerel: Os (all defaults)
set (CMAKE_CXX_FLAGS "-Wall -pedantic -Wextra -Wno-ignored-qualifiers")
set (CMAKE_Fortran_FLAGS "-std=legacy -Wfunction-elimination")
set (DEFAULT_BUILD_TYPE "Release")
#
if (CORSIKA_SCL_CXX)
add_definitions (-D_GLIBCXX_USE_CXX11_ABI=0)
endif()
# clang produces a lot of unecessary warnings without this:
add_compile_options (
$<$<OR:$<CXX_COMPILER_ID:Clang>,$<CXX_COMPILER_ID:AppleClang>>:-Wno-nonportable-include-path>
)
#
#+++++++++++++++++++++++++++++
# Build types settings
# Setup external dependencies.
#
# setup coverage build type
set (CMAKE_CXX_FLAGS_COVERAGE "-g --coverage")
set (CMAKE_EXE_LINKER_FLAGS_COVERAGE "--coverage")
set (CMAKE_SHARED_LINKER_FLAGS_COVERAGE "--coverage")
# set a flag to inform code that we are in debug mode
set (CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DDEBUG")
###
#
#+++++++++++++++++++++++++++++
# Build type selection
#
# Set the possible values of build type for cmake-gui and command line check
set (ALLOWED_BUILD_TYPES Debug Release MinSizeRel RelWithDebInfo Coverage)
set_property (CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS ${ALLOWED_BUILD_TYPES})
# Set a default build type if none was specified
# by default: "Debug", if local ".git" directory is found, otherwise "Release"
set (DEFAULT_BUILD_TYPE "Release")
if (EXISTS "${CMAKE_SOURCE_DIR}/.git")
set (DEFAULT_BUILD_TYPE "Debug")
endif ()
if (NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
message (STATUS "Setting build type to '${DEFAULT_BUILD_TYPE}' as no other was specified.")
set (CMAKE_BUILD_TYPE "${DEFAULT_BUILD_TYPE}" CACHE
STRING "Choose the type of build." FORCE)
else (NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
# Ignore capitalization when build type is selected manually and check for valid setting
string (TOLOWER ${CMAKE_BUILD_TYPE} SELECTED_LOWER)
string (TOLOWER "${ALLOWED_BUILD_TYPES}" BUILD_TYPES_LOWER)
if (NOT SELECTED_LOWER IN_LIST BUILD_TYPES_LOWER)
message (FATAL_ERROR "Unknown build type: ${CMAKE_BUILD_TYPE} [allowed: ${ALLOWED_BUILD_TYPES}]")
endif ()
message (STATUS "Build type is: ${CMAKE_BUILD_TYPE}")
endif (NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
# add cnpy temporarily. As long as SaveBoostHistogram does not save to parquet directly
#
add_subdirectory (externals/cnpy)
#+++++++++++++++++++++++++++++
# Coverage
#
# targets and settings needed to generate coverage reports
if (CMAKE_BUILD_TYPE STREQUAL Coverage)
#if (CMAKE_BUILD_TYPE STREQUAL Coverage)
SET(COVERAGE_BUILD OFF CACHE BOOL "Activate coverage build")
if( COVERAGE_BUILD AND (CMAKE_BUILD_TYPE STREQUAL "Debug"))
message(INFO "\n|==========> COVERAGE TARGET ACTIVATED.\n")
set (c8_lcov_download_url "https://github.com/linux-test-project/lcov/releases/download")
set (c8_lcov_version "1.16")
set (c8_lcov_install_dir "${CMAKE_BINARY_DIR}/lcov")
include(ExternalProject)
ExternalProject_Add(lcov
URL ${c8_lcov_download_url}/v${c8_lcov_version}/lcov-${c8_lcov_version}.tar.gz
DOWNLOAD_NO_EXTRACT 0
CONFIGURE_COMMAND ""
BUILD_COMMAND ""
INSTALL_COMMAND make -C <SOURCE_DIR> install PREFIX=${c8_lcov_install_dir}
)
find_package (Perl REQUIRED)
# compile coverage under -O0 to avoid any optimization, function elimation etc.
add_compile_options ("-O0")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -O0 --coverage")
# search for local lcov
find_program (c8_lcov_bin lcov)
if (NOT c8_lcov_bin)
set (c8_lcov_bin "${c8_lcov_install_dir}/bin/lcov")
message ("use C8 version of lcov ${c8_lcov_bin}")
endif ()
# search for local genhtml
find_program (c8_genhtml_bin genhtml)
if (NOT c8_genhtml_bin)
set (c8_genhtml_bin "${c8_lcov_install_dir}/bin/genhtml")
message ("use C8 version of genhtml ${c8_genhtml_bin}")
endif ()
set (GCOV gcov CACHE STRING "gcov executable" FORCE)
set (LCOV_BIN_DIR "${PROJECT_SOURCE_DIR}/externals/lcov/bin")
# collect coverage data
add_custom_command (
OUTPUT raw-coverage.info
COMMAND ${CMAKE_COMMAND} -E echo "Note: you need to run ctest at least once to generate the coverage data"
COMMAND ${LCOV_BIN_DIR}/lcov --gcov-tool=${GCOV} --directory . --capture --output-file raw-coverage.info
COMMAND ${c8_lcov_bin} --gcov-tool=${GCOV} --rc lcov_branch_coverage=1
--directory . --capture --output-file raw-coverage.info
)
# remove uninteresting entries
add_custom_command (
OUTPUT coverage.info
COMMAND ${LCOV_BIN_DIR}/lcov -q --remove raw-coverage.info "*/usr/*" "/usr/*" --output-file coverage2.info
COMMAND ${LCOV_BIN_DIR}/lcov --remove coverage2.info "*/externals/*" "*/tests/*" "*/sibyll2.3d.cpp" "*/include/Pythia8/*" "${CMAKE_CURRENT_SOURCE_DIR}/modules/*" "${CMAKE_CURRENT_BINARY_DIR}/modules/*" --output-file coverage.info
COMMAND ${c8_lcov_bin} -q --remove raw-coverage.info "*/usr/*" "/usr/*" --output-file coverage2.info
COMMAND ${c8_lcov_bin} --remove coverage2.info
"*/externals/*" "*/tests/*" "*/sibyll2.3d.cpp" "*/.conan/*"
"*/include/Pythia8/*" "*/install/*"
"${CMAKE_SOURCE_DIR}/modules/*" "${CMAKE_BINARY_DIR}/modules/*"
"*/cxroot/*" "*/.conan2/*" "/boost/*"
--output-file coverage.info
COMMAND ${CMAKE_COMMAND} -E remove coverage2.info
DEPENDS raw-coverage.info
)
# generate html report
add_custom_command (
OUTPUT coverage-report
COMMAND ${LCOV_BIN_DIR}/genhtml --demangle-cpp coverage.info -o coverage-report
COMMAND ${c8_genhtml_bin} --branch-coverage --show-details --title "CORSIKA 8 test coverage" --legend --demangle-cpp coverage.info -o coverage-report
DEPENDS coverage.info
)
add_custom_target (coverage DEPENDS coverage-report)
endif ()
#
#+++++++++++++++++++++++++++++
# CTest config
#
enable_testing ()
if (${CMAKE_VERSION} VERSION_LESS "3.12.0")
if (${CMAKE_VERSION} VERSION_LESS "3.12.0")
list (APPEND CMAKE_CTEST_ARGUMENTS "--output-on-failure")
else (${CMAKE_VERSION} VERSION_LESS "3.12.0")
set (CTEST_OUTPUT_ON_FAILURE 1) # this is for new versions of cmake
......@@ -155,102 +219,237 @@ set (CTEST_CUSTOM_COVERAGE_EXCLUDE "./tests/" "./examples/" "./modules/" "test*.
# include this test only if NOT run on gitlab-ci; On CI this is a dedicated job:
if (NOT DEFINED ENV{CI})
# add call to ./do-copyright.py to run as unit-test-case
add_test (NAME copyright_notices COMMAND ./do-copyright.py WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
add_test (NAME copyright_notices COMMAND ./do-copyright.py WORKING_DIRECTORY ${CMAKE_SOURCE_DIR})
endif (NOT DEFINED ENV{CI})
#
#+++++++++++++++++++++++++++++
# Options
#
# HISTORY option selection
option (WITH_HISTORY "Flag to switch on/off HISTORY" ON)
#
#+++++++++++++++++++++++++++++
# Externals
#
set (Python_ADDITIONAL_VERSIONS 3)
find_package (PythonInterp 3 REQUIRED)
#+++++++++++++++++++++++++++++++
# exporting of CMake targets
#
#+++++++++++++++++++++++++++++
# get Eigen3
#
find_package (Eigen3 3.3.4 REQUIRED)
#
#+++++++++++++++++++++++++++++
# get catch2
#
find_package (Catch2 2.13.2 REQUIRED)
#
#+++++++++++++++++++++++++++++
# use spdlog
#
add_subdirectory (externals/spdlog)
#
#+++++++++++++++++++++++++++++
# use zlib
#
find_package (ZLIB REQUIRED)
#
#+++++++++++++++++++++++++++++
# get phys_units
#
find_package (PhysUnits REQUIRED)
#
#
include (CMakePackageConfigHelpers)
# list of targets that will be INSTALLed and EXPORTed
# Important: all those targets must be individually INSTALLed with "EXPORT CORSIKA8PublicTargets"
set (public_CORSIKA8_targets CORSIKA8)
#+++++++++++++++++++++++++++++
# CORSIKA8
#
add_library (CORSIKA8 INTERFACE)
set_target_properties (
CORSIKA8
PROPERTIES
INTERFACE_CORSIKA8_MAJOR_VERSION 0
COMPATIBLE_INTERFACE_STRING CORSIKA8_MAJOR_VERSION
)
target_include_directories (
CORSIKA8
INTERFACE
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>
$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}>
$<INSTALL_INTERFACE:${CMAKE_INSTALL_PREFIX}>
$<BUILD_INTERFACE:${CMAKE_SOURCE_DIR}>
$<BUILD_INTERFACE:${CMAKE_BINARY_DIR}>
$<INSTALL_INTERFACE:include>
)
# since CORSIKA8 is a header only library we must specify all link dependencies here:
find_package(Boost COMPONENTS filesystem REQUIRED)
find_package(CLI11 REQUIRED)
find_package(Eigen3 REQUIRED)
find_package(spdlog REQUIRED)
find_package(yaml-cpp REQUIRED)
find_package(Arrow REQUIRED)
find_package(PROPOSAL REQUIRED)
find_package(Catch2 REQUIRED)
target_link_libraries (
CORSIKA8
INTERFACE
PhysUnits
BZip2::BZip2
Boost::filesystem
CLI11::CLI11
Eigen3::Eigen
spdlog::spdlog
yaml-cpp::yaml-cpp
Parquet::parquet_static
PROPOSAL::PROPOSAL
cnpy # for SaveBoostHistogram
)
# those are needed, since some headers (namely GeneratedParticleProperties.inc) are produced by python script from ParticleData.xml
# "src" is needed, since some headers (namely GeneratedParticleProperties.inc ec.) are produced by python script from e.g. ParticleData.xml
add_subdirectory (src)
#
#
add_subdirectory (documentation)
#+++++++++++++++++++++++++++++
# =~~~~~~~~~~~~~~~~~~~~~~~~~=
# = Add of subdirectories =
# =~~~~~~~~~~~~~~~~~~~~~~~~~=
#
#+++++++++++++++++++++++++++++
# modules
#
set (NO_BOOST 1) # do not use libboost_iostream in CorsikaData
add_subdirectory (modules/data)
add_subdirectory (modules/pythia)
set (CORSIKA_DATA_WITH_TEST ON) # we want to run the corsika-data unit test
add_subdirectory (modules/data) # this is corsika-data (submodule)
add_subdirectory (modules/common)
add_subdirectory (modules/pythia8)
add_subdirectory (modules/sibyll)
add_subdirectory (modules/sophia)
add_subdirectory (modules/qgsjetII)
add_subdirectory (modules/urqmd)
add_subdirectory (modules/conex)
add_subdirectory (modules/epos)
add_subdirectory (modules/tauola)
add_subdirectory (modules/fluka)
#
#+++++++++++++++++++++++++++++++
# tests
#
add_subdirectory (tests/framework)
add_subdirectory (tests/media)
add_subdirectory (tests/stack)
add_subdirectory (tests/modules)
# standard applications
#
add_subdirectory(applications)
#+++++++++++++++++++++++++++++++
# unit testing
#
add_subdirectory (tests)
#+++++++++++++++++++++++++++++++
# installation
#
install (
TARGETS CORSIKA8
EXPORT CORSIKA8PublicTargets
PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_PREFIX}
)
#
# header only part, just copy entire directory tree
#
install (DIRECTORY corsika DESTINATION include)
#
# generate cmake config package version (for find_package)
#
write_basic_package_version_file (
${PROJECT_BINARY_DIR}/corsikaConfigVersion.cmake
VERSION ${c8_version}
COMPATIBILITY SameMajorVersion
)
#
# export targets in build tree (for find_package)
#
export (
EXPORT CORSIKA8PublicTargets
FILE "${CMAKE_CURRENT_BINARY_DIR}/corsikaTargets.cmake"
NAMESPACE CORSIKA8::
)
#
# export targets in install tree (for find_package)
#
install (
EXPORT CORSIKA8PublicTargets
FILE corsikaTargets.cmake
NAMESPACE CORSIKA8::
DESTINATION lib/cmake/corsika
)
if(DEFINED CONAN_CMAKE_DIR)
install (
DIRECTORY conan_cmake/
DESTINATION lib/cmake/dependencies
)
endif(DEFINED CONAN_CMAKE_DIR)
#
# config for build tree (for find_package)
#
configure_package_config_file (
cmake/corsikaConfig.cmake.in
${PROJECT_BINARY_DIR}/corsikaConfig.cmake
INSTALL_DESTINATION ${CMAKE_INSTALL_PREFIX}
)
#
# corsikaDefines
#
configure_package_config_file (
cmake/corsikaDefines.cmake
${PROJECT_BINARY_DIR}/corsikaDefines.cmake
INSTALL_DESTINATION ${CMAKE_INSTALL_PREFIX}
)
#
# config for install tree (for find_package)
# overwrite with install locations (if it was build as part of corsika)
#
set (Pythia8_INCDIR ${Pythia8_INCDIR_INSTALL})
set (Pythia8_LIBDIR ${Pythia8_LIBDIR_INSTALL})
configure_package_config_file (
cmake/corsikaConfig.cmake.in
${PROJECT_BINARY_DIR}/corsikaConfig.cmake-install
INSTALL_DESTINATION ${CMAKE_INSTALL_PREFIX}
)
#
# generate "corsika/corsika.hpp" file with cmake-level details and paths
# first for build-tree
#
# the location of the "corsika-data" is of fundamental importance
set (CORSIKA_CMAKE_DATA_DIR ${CMAKE_SOURCE_DIR}/modules/data)
configure_file (
src/corsika.hpp.in
${PROJECT_BINARY_DIR}/corsika/corsika.hpp
)
#
# second also for install-tree
#
set (CORSIKA_CMAKE_DATA_DIR "${CMAKE_INSTALL_FULL_DATADIR}/corsika/data")
configure_file (
src/corsika.hpp.in
${PROJECT_BINARY_DIR}/corsika.hpp-install
)
#
# installation of cmake and config files
#
install (
FILES
${CMAKE_BINARY_DIR}/corsikaDefines.cmake
${CMAKE_BINARY_DIR}/corsikaConfigVersion.cmake
DESTINATION lib/cmake/corsika
)
#
# install and rename install-level corsikaConfig.cmake
#
install (
FILES
${CMAKE_BINARY_DIR}/corsikaConfig.cmake-install
RENAME corsikaConfig.cmake
DESTINATION lib/cmake/corsika
)
#
# also install-level config.hpp
#
install (FILES
${PROJECT_BINARY_DIR}/corsika.hpp-install
RENAME corsika.hpp
DESTINATION include/corsika
)
#
# examples
#
add_subdirectory (examples)
#
install (DIRECTORY examples DESTINATION ${CMAKE_INSTALL_DATADIR}/corsika)
#
# data
#
install (DIRECTORY modules/data DESTINATION ${CMAKE_INSTALL_DATADIR}/corsika)
#
# tools
#
add_subdirectory (tools)
#+++++++++++++++++++++++++++++++
#
# final summary output
#
include (FeatureSummary)
add_feature_info (HISTORY WITH_HISTORY "Full information on cascade history for particles.")
feature_summary (WHAT ALL)
# Collaboration agreement
The CORSIKA project very much welcomes all collaboration and
contributions. The aim of the CORSIKA project is to create a
scientific software framework as a fundamental tool for research. The
collaboration agreement and the licensing model are based on the
guidelines layed out by HSF
[[1]](https://hepsoftwarefoundation.org/activities/licensing.html) or
CERN
[[2]](https://www.google.com/url?sa=t&rct=j&q=&esrc=s&source=web&cd=1&ved=2ahUKEwiLqKG00dXdAhUOZFAKHdIwAh4QFjAAegQIARAC&url=https%3A%2F%2Findico.cern.ch%2Fcategory%2F4251%2Fattachments%2F101%2F505%2FOSL-2012-01-Open_Source_Licences_at_CERN-Short_version.pdf&usg=AOvVaw1n4S0PQCSeE6wbdfdhKDqF),
[[3]](http://legal.web.cern.ch/licensing/software), and follow the
examples of other big scientific software projects.
The CORSIKA project consists of the contributions from the scientific
community and individuals in a best effort to deliver the best
possible performance and physics output.
The MCnet guidelines developed by [www.montecarlonet.org](www.montecarlonet.org)
are copied in [MCNET_GUIDELINES](MCNET_GUIDELINES) -- they provide a very good
additional scope that contributors should read and consider.
All possible
liability and licensing question are only handled by the adopted
software license.
## The software license of the CORSIKA project
The license adopted for the CORSIKA project is the explicit copyleft
license GPLv3, as copied in full in the file
[LICENSE](LICENSE). Each source file of the CORSIKA project contains a
short statement of the copyright and this license. Each binary or
source code release of CORSIKA contains the file LICENSE. The
code, documentation and content in the folder [externals](externals)
is not integral part of the CORSIKA project and can be based on, or
include, other licenses, which must be compatible with GPLv3. Check the
content of this folder for details and additional license information. It depends on the configuration of
the build system to what extend this code is used to build CORSIKA.
## Contributing
If you want to contribute, you need to read
[the GUIDELINES](CONTRIBUTING.md) and comply with these rules, or help to
improve them.
## The CORSIKA Projects Maintainers
The CORSIKA Project mainters make all decisions for the CORSIKA
Project. They can also change the
[COLLABORATION\_AGREEMENT](COLLABORATION\_AGREEMENT.md), the
[GUIDELINES](CONTRIBUTING.md) or any other structure or document relevant for the CORSIKA Project.
The current CORSIKA Project maintainers are listed in the file [MAINTAINERS](MAINTAINERS.md).
and can be contacted via corsika-project@lists.kit.edu. The chair
person of the CORSIKA Project is Ralf Ulrich (KIT). Maintainers have special
responsibilities for specific parts of the project.
### Planning and performing releases
The CORSIKA maintainers decide on releases of the software, and about the content of it.
# Guidelines for code development, structure, formating etc.
The CORSIKA Project very much welcomes contributions. Here we outlined
The CORSIKA Project very much welcomes contributions. Here we outline
how you can find the right place to contribute, and how to do that.
Connect to https://gitlab.ikp.kit.edu and corsika-devel@lists.kit.edu (self-register at https://www.lists.kit.edu/sympa/subscribe/corsika-devel) to get in touch with the project.
The CORSIKA Project decides on the [GUIDELINES](CONTRIBUTING.md) and can decide to
Connect to https://gitlab.iap.kit.edu and corsika-devel@lists.kit.edu (self-register at https://www.lists.kit.edu/sympa/subscribe/corsika-devel) to get in touch with the project.
The CORSIKA Project decides on the [contributing guidelines](CONTRIBUTING.md) and can decide to
change/improve them.
# How to contribute
......@@ -20,7 +20,7 @@ change/improve them.
- Proposed code to close one issue (located in a specific git
branch) is reviewed, discussed, and eventually merged
into the master branch via a merge-request (MR) to close the issue.
- all merge request will undergo a code review, and must be approved before merge, in order to ensure high code qualtiy: [Code Approval Procedure](https://gitlab.ikp.kit.edu/AirShowerPhysics/corsika/-/wikis/Code-Approval-Procedure)
- all merge request will undergo a code review, and must be approved before merge, in order to ensure high code qualtiy: [Code Approval Procedure](https://gitlab.iap.kit.edu/AirShowerPhysics/corsika/-/wikis/Code-Approval-Procedure)
## Code formatting
......@@ -45,7 +45,7 @@ e.g. [link1](https://clangformat.com/) or
## Coding rules, conventions and guidelines
Please read the [Coding wiki page](https://gitlab.ikp.kit.edu/AirShowerPhysics/corsika/-/wikis/Coding-Conventions-and-Guidelines).
Please read the [Coding wiki page](https://gitlab.iap.kit.edu/AirShowerPhysics/corsika/-/wikis/Coding-Conventions-and-Guidelines).
......@@ -53,15 +53,14 @@ Please read the [Coding wiki page](https://gitlab.ikp.kit.edu/AirShowerPhysics/c
## Release versioning scheme
Releases of CORSIKA 8 are thought to be the baseline for larger scale
validation, and full production. The releases are numbered as x.y.z,
starting with x=8, which will not be changed for CORSIKA 8. The y index is
updated for new releases that normally contain improved or
validation, and full production. The releases are numbered as CORSIKA 8 vx.y.z,
starting with x=1. The x index is updated for new releases that normally contain improved or
enhanced physics performance, and also interface
changes to accomodate improvements. The z index can be updated more
changes to accomodate improvements. The y and z indices can be updated more
frequently for bug fixes or new features. Changes in z will not
contain interface changes, thus, production code will remain
fully compatible within changes of z. Special releases of CORSIKA will
also have a release names.
fully compatible within changes of z. Special releases of CORSIKA might
also have a release name.
# How to become scientific author of the CORSIKA Project
......@@ -70,9 +69,9 @@ The CORSIKA Project decides on who becomes scientific author. The
following conditions are sufficient, but not all of them are
required all the time:
- responsibility for a particular functionality or software/management part
- have read and follow these [GUIDELINES](CONTRIBUTING.md)
- have read and follow our [contributing guidelines](CONTRIBUTING.md)
- active in the CORSIKA Project, that means responsive to
discussions and problems in corsika-devel@list.kit.edu or on https//gitlab.ikp.kit.edu,
of relevant *Issues*, or in (phone) meetings
- agreement to the [COLLABORATION_AGREEMENT](COLLABORATION_AGREEMENT.md)
discussions and problems in corsika-devel@list.kit.edu or on https//gitlab.iap.kit.edu,
of relevant *Issues*, in (phone) meetings or our Mattermost workspace
- agreement to the [using and collaborating agreement](USING_COLLABORATING.md)
- the members of the CORSIKA Project must agree
Data @ 4d1785e7
Subproject commit 4d1785e74a7bf6769ee016509b357e63d7117438
/*
* (c) Copyright 2020 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#include <corsika/cascade/Cascade.h>
#include <corsika/environment/Environment.h>
#include <corsika/environment/LayeredSphericalAtmosphereBuilder.h>
#include <corsika/environment/NuclearComposition.h>
#include <corsika/environment/ShowerAxis.h>
#include <corsika/geometry/Plane.h>
#include <corsika/geometry/Sphere.h>
#include <corsika/process/ProcessSequence.h>
#include <corsika/process/StackProcess.h>
#include <corsika/process/longitudinal_profile/LongitudinalProfile.h>
#include <corsika/process/observation_plane/ObservationPlane.h>
#include <corsika/process/particle_cut/ParticleCut.h>
#include <corsika/process/proposal/ContinuousProcess.h>
#include <corsika/process/proposal/Interaction.h>
#include <corsika/process/track_writer/TrackWriter.h>
#include <corsika/random/RNGManager.h>
#include <corsika/setup/SetupStack.h>
#include <corsika/setup/SetupTrajectory.h>
#include <corsika/units/PhysicalUnits.h>
#include <corsika/utl/CorsikaFenv.h>
#include <corsika/process/interaction_counter/InteractionCounter.hpp>
#include <corsika/logging/Logging.h>
#include <iomanip>
#include <iostream>
#include <limits>
#include <string>
#include <typeinfo>
using namespace corsika;
using namespace corsika::process;
using namespace corsika::units;
using namespace corsika::particles;
using namespace corsika::random;
using namespace corsika::geometry;
using namespace corsika::environment;
using namespace std;
using namespace corsika::units::si;
void registerRandomStreams() {
random::RNGManager::GetInstance().RegisterRandomStream("cascade");
random::RNGManager::GetInstance().RegisterRandomStream("proposal");
random::RNGManager::GetInstance().SeedAll();
}
template <typename T>
using MyExtraEnv = environment::MediumPropertyModel<environment::UniformMagneticField<T>>;
int main(int argc, char** argv) {
logging::SetLevel(logging::level::info);
if (argc != 2) {
std::cerr << "usage: em_shower <energy/GeV>" << std::endl;
return 1;
}
feenableexcept(FE_INVALID);
// initialize random number sequence(s)
registerRandomStreams();
// setup environment, geometry
using EnvType = setup::Environment;
EnvType env;
const CoordinateSystem& rootCS = env.GetCoordinateSystem();
Point const center{rootCS, 0_m, 0_m, 0_m};
auto builder = environment::make_layered_spherical_atmosphere_builder<
setup::EnvironmentInterface,
MyExtraEnv>::create(center, units::constants::EarthRadius::Mean,
environment::Medium::AirDry1Atm,
geometry::Vector{rootCS, 0_T, 50_uT, 0_T});
builder.setNuclearComposition(
{{particles::Code::Nitrogen, particles::Code::Oxygen},
{0.7847f, 1.f - 0.7847f}}); // values taken from AIRES manual, Ar removed for now
builder.addExponentialLayer(1222.6562_g / (1_cm * 1_cm), 994186.38_cm, 4_km);
builder.addExponentialLayer(1144.9069_g / (1_cm * 1_cm), 878153.55_cm, 10_km);
builder.addExponentialLayer(1305.5948_g / (1_cm * 1_cm), 636143.04_cm, 40_km);
builder.addExponentialLayer(540.1778_g / (1_cm * 1_cm), 772170.16_cm, 100_km);
builder.addLinearLayer(1e9_cm, 112.8_km);
builder.assemble(env);
// setup particle stack, and add primary particle
setup::Stack stack;
stack.Clear();
const Code beamCode = Code::Electron;
auto const mass = particles::GetMass(beamCode);
const HEPEnergyType E0 = 1_GeV * std::stof(std::string(argv[1]));
double theta = 0.;
auto const thetaRad = theta / 180. * M_PI;
auto elab2plab = [](HEPEnergyType Elab, HEPMassType m) {
return sqrt((Elab - m) * (Elab + m));
};
HEPMomentumType P0 = elab2plab(E0, mass);
auto momentumComponents = [](double thetaRad, HEPMomentumType ptot) {
return std::make_tuple(ptot * sin(thetaRad), 0_eV, -ptot * cos(thetaRad));
};
auto const [px, py, pz] = momentumComponents(thetaRad, P0);
auto plab = corsika::stack::MomentumVector(rootCS, {px, py, pz});
cout << "input particle: " << beamCode << endl;
cout << "input angles: theta=" << theta << endl;
cout << "input momentum: " << plab.GetComponents() / 1_GeV << ", norm = " << plab.norm()
<< endl;
auto const observationHeight = 1.4_km + builder.getEarthRadius();
auto const injectionHeight = 112.75_km + builder.getEarthRadius();
auto const t = -observationHeight * cos(thetaRad) +
sqrt(-static_pow<2>(sin(thetaRad) * observationHeight) +
static_pow<2>(injectionHeight));
Point const showerCore{rootCS, 0_m, 0_m, observationHeight};
Point const injectionPos =
showerCore +
Vector<dimensionless_d>{rootCS, {-sin(thetaRad), 0, cos(thetaRad)}} * t;
std::cout << "point of injection: " << injectionPos.GetCoordinates() << std::endl;
stack.AddParticle(
std::tuple<particles::Code, units::si::HEPEnergyType,
corsika::stack::MomentumVector, geometry::Point, units::si::TimeType>{
beamCode, E0, plab, injectionPos, 0_ns});
std::cout << "shower axis length: " << (showerCore - injectionPos).norm() * 1.02
<< std::endl;
environment::ShowerAxis const showerAxis{injectionPos,
(showerCore - injectionPos) * 1.02, env};
// setup processes, decays and interactions
// PROPOSAL processs proposal{...};
process::particle_cut::ParticleCut cut(10_GeV, false, true);
process::proposal::Interaction proposal(env, cut.GetECut());
process::proposal::ContinuousProcess em_continuous(env, cut.GetECut());
process::interaction_counter::InteractionCounter proposalCounted(proposal);
process::track_writer::TrackWriter trackWriter("tracks.dat");
// long. profile; columns for gamma, e+, e- still need to be added
process::longitudinal_profile::LongitudinalProfile longprof{showerAxis};
Plane const obsPlane(showerCore, Vector<dimensionless_d>(rootCS, {0., 0., 1.}));
process::observation_plane::ObservationPlane observationLevel(
obsPlane, Vector<dimensionless_d>(rootCS, {1., 0., 0.}), "particles.dat");
auto sequence = process::sequence(proposalCounted, em_continuous, longprof, cut,
observationLevel, trackWriter);
// define air shower object, run simulation
setup::Tracking tracking;
cascade::Cascade EAS(env, tracking, sequence, stack);
// to fix the point of first interaction, uncomment the following two lines:
// EAS.SetNodes();
// EAS.forceInteraction();
EAS.Run();
cut.ShowResults();
em_continuous.showResults();
observationLevel.ShowResults();
const HEPEnergyType Efinal = cut.GetCutEnergy() + cut.GetInvEnergy() +
cut.GetEmEnergy() + em_continuous.energyLost() +
observationLevel.GetEnergyGround();
cout << "total cut energy (GeV): " << Efinal / 1_GeV << endl
<< "relative difference (%): " << (Efinal / E0 - 1) * 100 << endl;
observationLevel.Reset();
cut.Reset();
em_continuous.reset();
auto const hists = proposalCounted.GetHistogram();
hists.saveLab("inthist_lab_emShower.npz");
hists.saveCMS("inthist_cms_emShower.npz");
longprof.save("longprof_emShower.txt");
}
/*
* (c) Copyright 2018 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
/* clang-format off */
// InteractionCounter used boost/histogram, which
// fails if boost/type_traits have been included before. Thus, we have
// to include it first...
#include <corsika/process/interaction_counter/InteractionCounter.hpp>
/* clang-format on */
#include <corsika/cascade/Cascade.h>
#include <corsika/environment/Environment.h>
#include <corsika/environment/FlatExponential.h>
#include <corsika/environment/LayeredSphericalAtmosphereBuilder.h>
#include <corsika/environment/NuclearComposition.h>
#include <corsika/environment/ShowerAxis.h>
#include <corsika/geometry/Plane.h>
#include <corsika/geometry/Sphere.h>
#include <corsika/logging/Logging.h>
#include <corsika/process/ProcessSequence.h>
#include <corsika/process/SwitchProcessSequence.h>
#include <corsika/process/StackProcess.h>
#include <corsika/process/conex_source_cut/CONEXSourceCut.h>
#include <corsika/process/energy_loss/EnergyLoss.h>
#include <corsika/process/longitudinal_profile/LongitudinalProfile.h>
#include <corsika/process/observation_plane/ObservationPlane.h>
#include <corsika/process/on_shell_check/OnShellCheck.h>
#include <corsika/process/particle_cut/ParticleCut.h>
#include <corsika/process/pythia/Decay.h>
#include <corsika/process/sibyll/Decay.h>
#include <corsika/process/sibyll/Interaction.h>
#include <corsika/process/sibyll/NuclearInteraction.h>
#include <corsika/process/urqmd/UrQMD.h>
#include <corsika/random/RNGManager.h>
#include <corsika/setup/SetupStack.h>
#include <corsika/setup/SetupTrajectory.h>
#include <corsika/units/PhysicalUnits.h>
#include <corsika/utl/CorsikaFenv.h>
#include <iomanip>
#include <iostream>
#include <limits>
#include <string>
using namespace corsika;
using namespace corsika::process;
using namespace corsika::units;
using namespace corsika::particles;
using namespace corsika::random;
using namespace corsika::geometry;
using namespace corsika::environment;
using namespace std;
using namespace corsika::units::si;
void registerRandomStreams(const int seed) {
random::RNGManager::GetInstance().RegisterRandomStream("cascade");
random::RNGManager::GetInstance().RegisterRandomStream("qgsjet");
random::RNGManager::GetInstance().RegisterRandomStream("sibyll");
random::RNGManager::GetInstance().RegisterRandomStream("pythia");
random::RNGManager::GetInstance().RegisterRandomStream("urqmd");
random::RNGManager::GetInstance().RegisterRandomStream("proposal");
if (seed == 0)
random::RNGManager::GetInstance().SeedAll();
else
random::RNGManager::GetInstance().SeedAll(seed);
}
template <typename T>
using MyExtraEnv = environment::MediumPropertyModel<environment::UniformMagneticField<T>>;
int main(int argc, char** argv) {
logging::SetLevel(logging::level::info);
C8LOG_INFO("hybrid_MC");
if (argc < 4) {
std::cerr << "usage: hybrid_MC <A> <Z> <energy/GeV> [seed]" << std::endl;
std::cerr << " if no seed is given, a random seed is chosen" << std::endl;
return 1;
}
feenableexcept(FE_INVALID);
int seed = 0;
if (argc > 4) seed = std::stoi(std::string(argv[4]));
// initialize random number sequence(s)
registerRandomStreams(seed);
// setup environment, geometry
using EnvType = setup::Environment;
EnvType env;
const CoordinateSystem& rootCS = env.GetCoordinateSystem();
Point const center{rootCS, 0_m, 0_m, 0_m};
auto builder = environment::make_layered_spherical_atmosphere_builder<
setup::EnvironmentInterface,
MyExtraEnv>::create(center, units::constants::EarthRadius::Mean,
environment::Medium::AirDry1Atm,
geometry::Vector{rootCS, 0_T, 50_uT, 0_T});
builder.setNuclearComposition(
{{particles::Code::Nitrogen, particles::Code::Oxygen},
{0.7847f, 1.f - 0.7847f}}); // values taken from AIRES manual, Ar removed for now
builder.addExponentialLayer(1222.6562_g / (1_cm * 1_cm), 994186.38_cm, 4_km);
builder.addExponentialLayer(1144.9069_g / (1_cm * 1_cm), 878153.55_cm, 10_km);
builder.addExponentialLayer(1305.5948_g / (1_cm * 1_cm), 636143.04_cm, 40_km);
builder.addExponentialLayer(540.1778_g / (1_cm * 1_cm), 772170.16_cm, 100_km);
builder.addLinearLayer(1e9_cm, 112.8_km);
builder.assemble(env);
// setup particle stack, and add primary particle
setup::Stack stack;
stack.Clear();
const Code beamCode = Code::Nucleus;
unsigned short const A = std::stoi(std::string(argv[1]));
unsigned short Z = std::stoi(std::string(argv[2]));
auto const mass = particles::GetNucleusMass(A, Z);
const HEPEnergyType E0 = 1_GeV * std::stof(std::string(argv[3]));
double theta = 0.;
auto const thetaRad = theta / 180. * M_PI;
auto elab2plab = [](HEPEnergyType Elab, HEPMassType m) {
return sqrt((Elab - m) * (Elab + m));
};
HEPMomentumType P0 = elab2plab(E0, mass);
auto momentumComponents = [](double thetaRad, HEPMomentumType ptot) {
return std::make_tuple(ptot * sin(thetaRad), 0_eV, -ptot * cos(thetaRad));
};
auto const [px, py, pz] = momentumComponents(thetaRad, P0);
auto plab = corsika::stack::MomentumVector(rootCS, {px, py, pz});
cout << "input particle: " << beamCode << endl;
cout << "input angles: theta=" << theta << endl;
cout << "input momentum: " << plab.GetComponents() / 1_GeV << ", norm = " << plab.norm()
<< endl;
auto const observationHeight = 0_km + builder.getEarthRadius();
auto const injectionHeight = 112.75_km + builder.getEarthRadius();
auto const t = -observationHeight * cos(thetaRad) +
sqrt(-units::static_pow<2>(sin(thetaRad) * observationHeight) +
units::static_pow<2>(injectionHeight));
Point const showerCore{rootCS, 0_m, 0_m, observationHeight};
Point const injectionPos =
showerCore +
Vector<dimensionless_d>{rootCS, {-sin(thetaRad), 0, cos(thetaRad)}} * t;
std::cout << "point of injection: " << injectionPos.GetCoordinates() << std::endl;
if (A != 1) {
stack.AddParticle(std::tuple<particles::Code, units::si::HEPEnergyType,
corsika::stack::MomentumVector, geometry::Point,
units::si::TimeType, unsigned short, unsigned short>{
beamCode, E0, plab, injectionPos, 0_ns, A, Z});
} else {
stack.AddParticle(
std::tuple<particles::Code, units::si::HEPEnergyType,
corsika::stack::MomentumVector, geometry::Point, units::si::TimeType>{
particles::Code::Proton, E0, plab, injectionPos, 0_ns});
}
std::cout << "shower axis length: " << (showerCore - injectionPos).norm() * 1.02
<< std::endl;
environment::ShowerAxis const showerAxis{injectionPos,
(showerCore - injectionPos) * 1.02, env};
// setup processes, decays and interactions
process::sibyll::Interaction sibyll;
process::interaction_counter::InteractionCounter sibyllCounted(sibyll);
process::sibyll::NuclearInteraction sibyllNuc(sibyll, env);
process::interaction_counter::InteractionCounter sibyllNucCounted(sibyllNuc);
process::pythia::Decay decayPythia;
// use sibyll decay routine for decays of particles unknown to pythia
process::sibyll::Decay decaySibyll{{
Code::N1440Plus,
Code::N1440MinusBar,
Code::N1440_0,
Code::N1440_0Bar,
Code::N1710Plus,
Code::N1710MinusBar,
Code::N1710_0,
Code::N1710_0Bar,
Code::Pi1300Plus,
Code::Pi1300Minus,
Code::Pi1300_0,
Code::KStar0_1430_0,
Code::KStar0_1430_0Bar,
Code::KStar0_1430_Plus,
Code::KStar0_1430_MinusBar,
}};
decaySibyll.PrintDecayConfig();
process::particle_cut::ParticleCut cut{60_GeV, false, true};
process::energy_loss::EnergyLoss eLoss{showerAxis, cut.GetECut()};
corsika::process::conex_source_cut::CONEXSourceCut conex(
center, showerAxis, t, injectionHeight, E0,
particles::GetPDG(particles::Code::Proton));
process::on_shell_check::OnShellCheck reset_particle_mass(1.e-3, 1.e-1, false);
process::longitudinal_profile::LongitudinalProfile longprof{showerAxis};
Plane const obsPlane(showerCore, Vector<dimensionless_d>(rootCS, {0., 0., 1.}));
process::observation_plane::ObservationPlane observationLevel(
obsPlane, Vector<dimensionless_d>(rootCS, {1., 0., 0.}), "particles.dat");
process::UrQMD::UrQMD urqmd;
process::interaction_counter::InteractionCounter urqmdCounted{urqmd};
// assemble all processes into an ordered process list
struct EnergySwitch {
HEPEnergyType cutE_;
EnergySwitch(HEPEnergyType cutE)
: cutE_(cutE) {}
process::SwitchResult operator()(const setup::Stack::ParticleType& p) {
if (p.GetEnergy() < cutE_)
return process::SwitchResult::First;
else
return process::SwitchResult::Second;
}
};
auto hadronSequence =
process::select(urqmdCounted, process::sequence(sibyllNucCounted, sibyllCounted),
EnergySwitch(55_GeV));
auto decaySequence = process::sequence(decayPythia, decaySibyll);
auto sequence = process::sequence(hadronSequence, reset_particle_mass, decaySequence,
eLoss, cut, conex, longprof, observationLevel);
// define air shower object, run simulation
setup::Tracking tracking;
cascade::Cascade EAS(env, tracking, sequence, stack);
// to fix the point of first interaction, uncomment the following two lines:
// EAS.SetNodes();
// EAS.forceInteraction();
EAS.Run();
cut.ShowResults();
eLoss.showResults();
observationLevel.ShowResults();
const HEPEnergyType Efinal = cut.GetCutEnergy() + cut.GetInvEnergy() +
cut.GetEmEnergy() + eLoss.energyLost() +
observationLevel.GetEnergyGround();
cout << "total cut energy (GeV): " << Efinal / 1_GeV << endl
<< "relative difference (%): " << (Efinal / E0 - 1) * 100 << endl;
observationLevel.Reset();
cut.Reset();
eLoss.reset();
conex.SolveCE();
auto const hists = sibyllCounted.GetHistogram() + sibyllNucCounted.GetHistogram() +
urqmdCounted.GetHistogram();
hists.saveLab("inthist_lab.txt");
hists.saveCMS("inthist_cms.txt");
hists.saveLab("inthist_lab.txt");
hists.saveCMS("inthist_cms.txt");
longprof.save("longprof.txt");
std::ofstream finish("finished");
finish << "run completed without error" << std::endl;
}
/*
* (c) Copyright 2018 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#include <corsika/particles/ParticleProperties.h>
#include <corsika/process/ProcessSequence.h>
#include <corsika/process/qgsjetII/ParticleConversion.h>
#include <corsika/process/sibyll/ParticleConversion.h>
#include <corsika/setup/SetupEnvironment.h>
#include <corsika/units/PhysicalUnits.h>
#include <iomanip>
#include <iostream>
#include <string>
using namespace corsika::units;
using namespace corsika::units::si;
using namespace corsika::particles;
using namespace std;
//
// The example main program for a particle list
//
int main() {
std::cout << "particle_list_example" << std::endl;
cout << "------------------------------------------"
<< "particles in CORSIKA"
<< "------------------------------------------" << endl;
cout << std::setw(20) << "Name"
<< " | " << std::setw(10) << "PDG-id"
<< " | " << std::setw(10) << "SIBYLL-id"
<< " | " << std::setw(10) << "QGSJETII-id"
<< " | " << std::setw(18) << "PDG-mass (GeV)"
<< " | " << std::setw(18) << "SIBYLL-mass (GeV)"
<< " | " << endl;
cout << std::setw(104) << std::setfill('-') << "-" << endl;
for (auto p : getAllParticles()) {
if (!IsNucleus(p)) {
corsika::process::sibyll::SibyllCode sib_id =
corsika::process::sibyll::ConvertToSibyll(p);
auto const sib_mass =
(sib_id != corsika::process::sibyll::SibyllCode::Unknown
? to_string(corsika::process::sibyll::GetSibyllMass(p) / 1_GeV)
: "--");
auto const qgs_id = corsika::process::qgsjetII::ConvertToQgsjetII(p);
cout << std::setw(20) << std::setfill(' ') << p << " | " << std::setw(10)
<< static_cast<int>(GetPDG(p)) << " | " << std::setw(10)
<< (sib_id != corsika::process::sibyll::SibyllCode::Unknown
? to_string(static_cast<int>(sib_id))
: "--")
<< " | " << std::setw(10)
<< (qgs_id != corsika::process::qgsjetII::QgsjetIICode::Unknown
? to_string(static_cast<int>(qgs_id))
: "--")
<< " | " << std::setw(18) << std::setprecision(5) << GetMass(p) / 1_GeV
<< " | " << std::setw(18) << std::setprecision(5) << sib_mass << " | " << endl;
}
}
cout << std::setw(104) << std::setfill('-') << "-" << endl;
}
/*
* (c) Copyright 2020 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#pragma once
namespace corsika::environment {
/**
* Medium types are useful most importantly for effective models
* like energy losses. a particular medium (mixture of components)
* may have specif properties not reflected by its mixture of
* components.
**/
enum class MediumType {
Unknown,
Element,
RadioactiveElement,
InorganicCompound,
OrganicCompound,
Polymer,
Mixture,
BiologicalDosimetry
};
enum class State { Unknown, Solid, Liquid, Gas, DiatomicGas };
enum class Medium : int16_t;
using MediumIntType = std::underlying_type<Medium>::type;
/**
* \struct MediumData
*
* Simple object to group together a number of properties
*
**/
struct MediumData {
std::string name_;
std::string pretty_name_;
double weight_;
int weight_significant_figure_;
int weight_error_last_digit_;
double Z_over_A_;
double sternheimer_density_;
double corrected_density_;
State state_;
MediumType type_;
std::string symbol_;
double Ieff_;
double Cbar_;
double x0_;
double x1_;
double aa_;
double sk_;
double dlt0_;
std::string name() const { return name_; }
std::string pretty_name() const { return pretty_name_; }
double weight() const { return weight_; }
int weight_significant_figure() const { return weight_significant_figure_; }
int weight_error_last_digit() const { return weight_error_last_digit_; }
double Z_over_A() const { return Z_over_A_; }
double sternheimer_density() const { return sternheimer_density_; }
double corrected_density() const { return corrected_density_; }
State state() const { return state_; }
MediumType type() const { return type_; }
std::string symbol() const { return symbol_; }
double Ieff() const { return Ieff_; }
double Cbar() const { return Cbar_; }
double x0() const { return x0_; }
double x1() const { return x1_; }
double aa() const { return aa_; }
double sk() const { return sk_; }
double dlt0() const { return dlt0_; }
};
} // namespace corsika::environment
#include <corsika/environment/GeneratedMediaProperties.inc>
namespace corsika::environment {
constexpr MediumData const& mediumData(Medium const m) {
return detail::medium_data[static_cast<MediumIntType>(m)];
}
} // namespace corsika::environment
/*
* (c) Copyright 2020 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#pragma once
namespace corsika::environment {
/**
* Medium types are useful most importantly for effective models
* like energy losses. a particular medium (mixture of components)
* may have specif properties not reflected by its mixture of
* components.
*/
enum class EMediumType { eUnknown, eAir, eWater, eIce, eRock };
} // namespace corsika::environment
/*
* (c) Copyright 2020 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#pragma once
#include <corsika/environment/IMagneticFieldModel.h>
#include <corsika/geometry/RootCoordinateSystem.h>
namespace corsika::environment {
/**
* A uniform (constant) magnetic field.
*
* This class returns the same magnetic field vector
* for all evaluated locations.
*
*/
template <typename T>
class NoMagneticField : public T {
// a type-alias for a magnetic field vector
using MagneticFieldVector =
corsika::geometry::Vector<corsika::units::si::magnetic_flux_density_d>;
public:
/**
* Construct a NoMagneticField.
*
* This is initialized with a fixed magnetic field
* and returns this magnetic field at all locations.
*
* @param field The fixed magnetic field to return.
*/
template <typename... Args>
NoMagneticField(Args&&... args)
: T(std::forward<Args>(args)...) {}
/**
* Evaluate the magnetic field at a given location.
*
* @param point The location to evaluate the field at.
* @returns The magnetic field vector.
*/
MagneticFieldVector GetMagneticField(
corsika::geometry::Point const&) const final override {
CoordinateSystem const& gCS =
RootCoordinateSystem::GetInstance().GetRootCoordinateSystem();
return MagneticFieldVector(gCS, {0_T, 0_T, 0_T});
}
}; // END: class MagneticField
} // namespace corsika::environment
/*
* (c) Copyright 2020 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#include <corsika/environment/ShowerAxis.h>
#include <corsika/logging/Logging.h>
#include <string>
using namespace corsika::environment;
using namespace corsika::units::si;
using namespace corsika;
GrammageType ShowerAxis::X(LengthType l) const {
double const fractionalBin = l / steplength_;
int const lower = fractionalBin; // indices of nearest X support points
double const frac = fractionalBin - lower;
unsigned int const upper = lower + 1;
if (fractionalBin < 0) {
C8LOG_ERROR("cannot extrapolate to points behind point of injection l={} m", l / 1_m);
if (throw_) {
throw std::runtime_error("cannot extrapolate to points behind point of injection");
}
return minimumX();
}
if (upper >= X_.size()) {
const std::string err =
fmt::format("shower axis too short, cannot extrapolate (l / max_length_ = {} )",
l / max_length_);
C8LOG_ERROR(err);
if (throw_) { throw std::runtime_error(err.c_str()); }
return maximumX();
}
C8LOG_TRACE("showerAxis::X frac={}, fractionalBin={}, lower={}, upper={}", frac,
fractionalBin, lower, upper);
assert(0 <= frac && frac <= 1.);
C8LOG_TRACE("ShowerAxis::X l={} m, lower={}, frac={}, upper={}", l / 1_m, lower, frac,
upper);
// linear interpolation between X[lower] and X[upper]
return X_[upper] * frac + X_[lower] * (1 - frac);
}
LengthType ShowerAxis::steplength() const { return steplength_; }
GrammageType ShowerAxis::maximumX() const { return *X_.rbegin(); }
GrammageType ShowerAxis::minimumX() const { return GrammageType::zero(); }
GrammageType ShowerAxis::projectedX(geometry::Point const& p) const {
auto const projectedLength = (p - pointStart_).dot(axis_normalized_);
return X(projectedLength);
}
geometry::Vector<units::si::dimensionless_d> const& ShowerAxis::GetDirection() const {
return axis_normalized_;
}
geometry::Point const& ShowerAxis::GetStart() const { return pointStart_; }
/*
* (c) Copyright 2020 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#pragma once
#include <corsika/environment/Environment.h>
#include <corsika/geometry/Point.h>
#include <corsika/geometry/Vector.h>
#include <corsika/units/PhysicalUnits.h>
#include <cassert>
#include <cstdlib>
#include <fstream>
#include <functional>
#include <iterator>
#include <memory>
#include <stdexcept>
#include <vector>
#include <iostream>
#include <boost/math/quadrature/gauss_kronrod.hpp>
namespace corsika::environment {
/**
* \class ShowerAxis
*
* The environment::ShowerAxis is created from a geometry::Point and
* a geometry::Vector and inside an Environment. It internally uses
* a table with steps=10000 (default) rows for interpolation.
*
* The shower axis can convert location in the shower into a
* projected grammage along the shower axis.
*
**/
class ShowerAxis {
public:
template <typename TEnvModel>
ShowerAxis(geometry::Point const& pStart,
geometry::Vector<units::si::length_d> length,
environment::Environment<TEnvModel> const& env, bool doThrow = false,
int steps = 10'000)
: pointStart_(pStart)
, length_(length)
, throw_(doThrow)
, max_length_(length_.norm())
, steplength_(max_length_ / steps)
, axis_normalized_(length / max_length_)
, X_(steps + 1) {
auto const* const universe = env.GetUniverse().get();
auto rho = [pStart, length, universe](double x) {
auto const p = pStart + length * x;
auto const* node = universe->GetContainingNode(p);
return node->GetModelProperties().GetMassDensity(p).magnitude();
};
double error;
int k = 0;
X_[0] = units::si::GrammageType::zero();
auto sum = units::si::GrammageType::zero();
for (int i = 1; i <= steps; ++i) {
auto const x_prev = (i - 1.) / steps;
auto const d_prev = max_length_ * x_prev;
auto const x = double(i) / steps;
auto const r = boost::math::quadrature::gauss_kronrod<double, 15>::integrate(
rho, x_prev, x, 15, 1e-9, &error);
auto const result =
units::si::MassDensityType(phys::units::detail::magnitude_tag, r) *
max_length_;
sum += result;
X_[i] = sum;
for (; sum > k * X_binning_; ++k) {
d_.emplace_back(d_prev + k * X_binning_ * steplength_ / result);
}
}
assert(std::is_sorted(X_.cbegin(), X_.cend()));
assert(std::is_sorted(d_.cbegin(), d_.cend()));
}
units::si::LengthType steplength() const;
units::si::GrammageType maximumX() const;
units::si::GrammageType minimumX() const;
units::si::GrammageType projectedX(geometry::Point const& p) const;
units::si::GrammageType X(units::si::LengthType) const;
geometry::Vector<units::si::dimensionless_d> const& GetDirection() const;
geometry::Point const& GetStart() const;
private:
geometry::Point const pointStart_;
geometry::Vector<units::si::length_d> const length_;
bool throw_ = false;
units::si::LengthType const max_length_, steplength_;
geometry::Vector<units::si::dimensionless_d> const axis_normalized_;
std::vector<units::si::GrammageType> X_;
// for storing the lengths corresponding to equidistant X values
units::si::GrammageType const X_binning_ = std::invoke([]() {
using namespace units::si;
return 1_g / 1_cm / 1_cm;
});
std::vector<units::si::LengthType> d_;
};
} // namespace corsika::environment
/*
* (c) Copyright 2018 CORSIKA Project, corsika-project@lists.kit.edu
*
* This software is distributed under the terms of the GNU General Public
* Licence version 3 (GPL Version 3). See file LICENSE for a full version of
* the license.
*/
#include <corsika/environment/DensityFunction.h>
#include <corsika/environment/HomogeneousMedium.h>
#include <corsika/environment/IMediumModel.h>
#include <corsika/environment/NuclearComposition.h>
#include <corsika/environment/ShowerAxis.h>
#include <corsika/environment/VolumeTreeNode.h>
#include <corsika/geometry/Line.h>
#include <corsika/geometry/RootCoordinateSystem.h>
#include <corsika/geometry/Vector.h>
#include <corsika/particles/ParticleProperties.h>
#include <corsika/units/PhysicalUnits.h>
#include <catch2/catch.hpp>
using namespace corsika::geometry;
using namespace corsika::environment;
using namespace corsika::particles;
using namespace corsika::units;
using namespace corsika::units::si;
using namespace corsika;
const auto density = 1_kg / (1_m * 1_m * 1_m);
auto setupEnvironment(particles::Code vTargetCode) {
// setup environment, geometry
auto env = std::make_unique<environment::Environment<environment::IMediumModel>>();
auto& universe = *(env->GetUniverse());
const geometry::CoordinateSystem& cs = env->GetCoordinateSystem();
auto theMedium =
environment::Environment<environment::IMediumModel>::CreateNode<geometry::Sphere>(
geometry::Point{cs, 0_m, 0_m, 0_m},
1_km * std::numeric_limits<double>::infinity());
using MyHomogeneousModel = environment::HomogeneousMedium<environment::IMediumModel>;
theMedium->SetModelProperties<MyHomogeneousModel>(
density, environment::NuclearComposition(std::vector<particles::Code>{vTargetCode},
std::vector<float>{1.}));
auto const* nodePtr = theMedium.get();
universe.AddChild(std::move(theMedium));
return std::make_tuple(std::move(env), &cs, nodePtr);
}
TEST_CASE("Homogeneous Density") {
auto [env, csPtr, nodePtr] = setupEnvironment(particles::Code::Nitrogen);
auto const& cs = *csPtr;
[[maybe_unused]] auto const& env_dummy = env;
[[maybe_unused]] auto const& node_dummy = nodePtr;
auto const observationHeight = 0_km;
auto const injectionHeight = 10_km;
auto const t = -observationHeight + injectionHeight;
Point const showerCore{cs, 0_m, 0_m, observationHeight};
Point const injectionPos = showerCore + Vector<dimensionless_d>{cs, {0, 0, 1}} * t;
environment::ShowerAxis const showerAxis{injectionPos, (showerCore - injectionPos),
*env,
false, // -> do not throw exceptions
20}; // -> number of bins
CHECK(showerAxis.steplength() == 500_m);
CHECK(showerAxis.maximumX() / (10_km * density) == Approx(1).epsilon(1e-8));
CHECK(showerAxis.minimumX() == 0_g / square(1_cm));
const Point p{cs, 10_km, 20_km, 8.3_km};
CHECK(showerAxis.projectedX(p) / (1.7_km * density) == Approx(1).epsilon(1e-8));
const units::si::LengthType d = 6.789_km;
CHECK(showerAxis.X(d) / (d * density) == Approx(1).epsilon(1e-8));
const Vector<dimensionless_d> dir{cs, {0, 0, -1}};
CHECK(showerAxis.GetDirection().GetComponents(cs) == dir.GetComponents(cs));
CHECK(showerAxis.GetStart().GetCoordinates() == injectionPos.GetCoordinates());
}
# create the library
add_library (CORSIKAanalytics INTERFACE)
# namespace of library -> location of header files
set (
CORSIKAanalytics_NAMESPACE
corsika/analytics
)
# header files of this library
set (
CORSIKAanalytics_HEADERS
ClassTimer.h
FunctionTimer.h
)
# copy the headers into the namespace
CORSIKA_COPY_HEADERS_TO_NAMESPACE (CORSIKAanalytics
${CORSIKAanalytics_NAMESPACE}
${CORSIKAanalytics_HEADERS}
)
# include directive for upstream code
target_include_directories (
CORSIKAanalytics
INTERFACE
$<BUILD_INTERFACE:${PROJECT_BINARY_DIR}/include>
$<INSTALL_INTERFACE:include/>
C8::ext:boost
)
# and link against spdlog
#target_link_libraries(
# CORSIKAanalytics
# INTERFACE
# spdlog::spdlog
#)
# install library
install (
FILES ${CORSIKAanalytics_HEADERS}
DESTINATION include/${CORSIKAanalytics_NAMESPACE}
)
# ----------------
# code unit testing
CORSIKA_ADD_TEST (testFunctionTimer)
target_link_libraries (
testFunctionTimer
CORSIKAanalytics
CORSIKAtesting
)
CORSIKA_ADD_TEST (testClassTimer)
target_link_libraries (
testClassTimer
CORSIKAanalytics
CORSIKAtesting
)