diff --git a/.gitmodules b/.gitmodules
index a83e793ed130c428ed818e68bc9ba1c50e05af7b..39ac29ed6afd0e4865fef71904e6d65b7209da30 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -28,9 +28,6 @@
 [submodule "ThirdParty/googletest"]
 	path = ThirdParty/googletest
 	url = https://github.com/google/googletest.git
-[submodule "ThirdParty/jedbrown-cmake-modules"]
-	path = ThirdParty/jedbrown-cmake-modules
-	url = https://github.com/jedbrown/cmake-modules.git
 [submodule "ThirdParty/exprtk"]
 	path = ThirdParty/exprtk
 	url = https://github.com/ArashPartow/exprtk.git
@@ -46,3 +43,6 @@
 [submodule "ThirdParty/ogs6py"]
 	path = ThirdParty/ogs6py
 	url = https://github.com/joergbuchwald/ogs6py.git
+[submodule "ThirdParty/json-cmake"]
+	path = ThirdParty/json-cmake
+	url = https://github.com/ufz/json-cmake.git
diff --git a/CMakeLists.txt b/CMakeLists.txt
index d15d2dd0cbf34157b172b3786c1be9051fef1d8c..4139f13aeb92c66ac9fef400141b187e0312ad17 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -62,9 +62,10 @@ option(OGS_USE_CVODE "Use the Sundials CVODE module?" OFF)
 
 # ---- CMake includes ----
 include(PreFind)
+include(SubmoduleSetup)
+include(Versions)
 include(CheckTypeSizes)
 include(Functions)
-include(SubmoduleSetup)
 include(ConanSetup)
 include(CompilerSetup)
 include(Find)
diff --git a/ThirdParty/jedbrown-cmake-modules b/ThirdParty/jedbrown-cmake-modules
deleted file mode 160000
index 91f96174a8b3f65e19519fa592b1571391c0e3d0..0000000000000000000000000000000000000000
--- a/ThirdParty/jedbrown-cmake-modules
+++ /dev/null
@@ -1 +0,0 @@
-Subproject commit 91f96174a8b3f65e19519fa592b1571391c0e3d0
diff --git a/ThirdParty/json-cmake b/ThirdParty/json-cmake
new file mode 160000
index 0000000000000000000000000000000000000000..9708cb091f6b89b94d71ae98f8b9e68ea04c47dd
--- /dev/null
+++ b/ThirdParty/json-cmake
@@ -0,0 +1 @@
+Subproject commit 9708cb091f6b89b94d71ae98f8b9e68ea04c47dd
diff --git a/scripts/cmake/CMakeSetup.cmake b/scripts/cmake/CMakeSetup.cmake
index 282d0019edb2b650e3a80160a01de6bea01ca4b0..dbd4489d3f8a5c1111a9acf06e313d55c62da352 100644
--- a/scripts/cmake/CMakeSetup.cmake
+++ b/scripts/cmake/CMakeSetup.cmake
@@ -9,8 +9,8 @@ endif()
 # Set additional CMake modules path
 set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH}
   "${PROJECT_SOURCE_DIR}/scripts/cmake"
-  "${PROJECT_SOURCE_DIR}/ThirdParty/cmake-modules"
-  "${PROJECT_SOURCE_DIR}/ThirdParty/jedbrown-cmake-modules")
+  "${PROJECT_SOURCE_DIR}/scripts/cmake/jedbrown"
+  "${PROJECT_SOURCE_DIR}/ThirdParty/cmake-modules")
 
 list(APPEND CMAKE_PREFIX_PATH
   $ENV{HOMEBREW_ROOT}             # Homebrew package manager on Mac OS
diff --git a/scripts/cmake/CompilerSetup.cmake b/scripts/cmake/CompilerSetup.cmake
index 03bd4dafc37b2362bb647df5d55d3da481c94744..32b4c305504741ac95c0a00207a51c390ca4eaf9 100644
--- a/scripts/cmake/CompilerSetup.cmake
+++ b/scripts/cmake/CompilerSetup.cmake
@@ -95,18 +95,18 @@ if(COMPILER_IS_GCC OR COMPILER_IS_CLANG OR COMPILER_IS_INTEL)
     endif()
 
     if(COMPILER_IS_GCC)
-        if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS "7.3")
-            message(FATAL_ERROR "GCC minimum required version is 7.3! You are \
-                using ${CMAKE_CXX_COMPILER_VERSION}.")
+        if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS ${ogs.minimum_version.gcc})
+            message(FATAL_ERROR "GCC minimum required version is ${OGS_GCC_MINIMUM_VERSION}! \
+                You are using ${CMAKE_CXX_COMPILER_VERSION}.")
         endif()
         add_compile_options(-fext-numeric-literals)
         include(GCCSanitizer)
     endif()
 
     if(COMPILER_IS_CLANG)
-        if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS "3.5")
-            message(FATAL_ERROR "Aborting: Clang 3.5 is required! Found version \
-                ${CMAKE_CXX_COMPILER_VERSION}")
+        if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS ${ogs.minimum_version.clang})
+            message(FATAL_ERROR "Aborting: Clang ${OGS_CLANG_MINIMUM_VERSION} \
+                is required! Found version ${CMAKE_CXX_COMPILER_VERSION}")
         endif()
         include(ClangSanitizer)
     endif()
@@ -118,6 +118,12 @@ if(COMPILER_IS_GCC OR COMPILER_IS_CLANG OR COMPILER_IS_INTEL)
 endif()
 
 if(MSVC)
+    if(${MSVC_TOOLSET_VERSION} LESS ${ogs.minimum_version.msvc.toolset})
+        message(FATAL_ERROR "Aborting: Visual Studio ${ogs.minimum_version.msvc.year} \
+            is required! Found Visual Studio with toolset version \
+            ${MSVC_TOOLSET_VERSION}. See the following link for version info: \
+            https://cmake.org/cmake/help/v3.16/variable/MSVC_TOOLSET_VERSION.html")
+    endif()
     if(OGS_CPU_ARCHITECTURE STREQUAL "native")
         set(CPU_FLAGS /favor:blend)
     else()
diff --git a/scripts/cmake/ConanSetup.cmake b/scripts/cmake/ConanSetup.cmake
index f5ab82633f3a1c02daeda6b54c1388b15e5bc956..0784e47816c8c90c05a2214a70aa1e3b69df73ff 100644
--- a/scripts/cmake/ConanSetup.cmake
+++ b/scripts/cmake/ConanSetup.cmake
@@ -105,7 +105,7 @@ if(OGS_USE_NETCDF)
     set(CONAN_REQUIRES ${CONAN_REQUIRES} netcdf-cxx/4.3.1@bilke/testing)
 endif()
 
-conan_check(VERSION 1.21.0)
+conan_check(VERSION ${ogs.minimum_version.conan})
 
 message(STATUS "Third-party libraries:")
 foreach(LIB ${OGS_LIBS})
diff --git a/scripts/cmake/Find.cmake b/scripts/cmake/Find.cmake
index ff9508ac5fe2cf2ceb20f568319627f7d136331a..91861612998b8914ea440469df762773c168d851 100644
--- a/scripts/cmake/Find.cmake
+++ b/scripts/cmake/Find.cmake
@@ -2,6 +2,12 @@
 ### Find tools     ###
 ######################
 
+string(REPLACE ".windows.1" "" GIT_VERSION_STRING ${GIT_VERSION_STRING})
+if(${GIT_VERSION_STRING} VERSION_LESS ${ogs.minimum_version.git})
+    message(FATAL_ERROR "Git version ${ogs.minimum_version.git} is required. \
+        Found version ${GIT_VERSION_STRING}.")
+endif()
+
 find_package(Doxygen OPTIONAL_COMPONENTS dot)
 
 # Find gnu profiler gprof
diff --git a/scripts/cmake/PreFind.cmake b/scripts/cmake/PreFind.cmake
index 6c028cb857b3b272504b6f0862dab5099a9e2ab7..2af46e8a8c2d3e75087c69bb9bd9f0621dfb6591 100644
--- a/scripts/cmake/PreFind.cmake
+++ b/scripts/cmake/PreFind.cmake
@@ -1,15 +1,4 @@
-### Find Git
-# Check for cmder git installed via chocolatey
-find_program(GIT_EXECUTABLE
-  NAMES git
-  PATHS C:/tools/cmder/vendor/git-for-windows
-  PATH_SUFFIXES cmd bin
-  DOC "Git command line client"
-)
-
 find_package(Git REQUIRED)
-string(REPLACE "mingw64/" "" GIT_EXECUTABLE ${GIT_EXECUTABLE}) # Windows git submodule fix
-### End Find Git
 
 execute_process(COMMAND ${GIT_EXECUTABLE} status
     WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
diff --git a/scripts/cmake/SubmoduleSetup.cmake b/scripts/cmake/SubmoduleSetup.cmake
index 14b87e8af07f2f5bcb09c2cf1f5a9ee90f17039f..2c62fa9a3193a7c5c2c677a33d7e3b0f30a128ff 100644
--- a/scripts/cmake/SubmoduleSetup.cmake
+++ b/scripts/cmake/SubmoduleSetup.cmake
@@ -14,7 +14,7 @@ set(REQUIRED_SUBMODULES
     ThirdParty/exprtk
     ThirdParty/googletest
     ThirdParty/iphreeqc/src
-    ThirdParty/jedbrown-cmake-modules
+    ThirdParty/json-cmake
     ThirdParty/tclap
     ThirdParty/tetgen
     ThirdParty/vtkdiff
diff --git a/scripts/cmake/Versions.cmake b/scripts/cmake/Versions.cmake
new file mode 100644
index 0000000000000000000000000000000000000000..7d9eed4199c3e840e375473ae7b4c3952e831388
--- /dev/null
+++ b/scripts/cmake/Versions.cmake
@@ -0,0 +1,8 @@
+include(${PROJECT_SOURCE_DIR}/ThirdParty/json-cmake/JSONParser.cmake)
+file(READ ${PROJECT_SOURCE_DIR}/web/data/versions.json jsonFileString)
+sbeParseJson(ogs jsonFileString)
+# Provides variables, e.g. ogs.minimum_version.gcc
+# Output all variables with
+#   foreach(var ${ogs})
+#     message("${var} = ${${var}}")
+#   endforeach()
diff --git a/scripts/cmake/jedbrown/FindPETSc.cmake b/scripts/cmake/jedbrown/FindPETSc.cmake
new file mode 100644
index 0000000000000000000000000000000000000000..41e02d9798c47f32ae57e7ecff2f544eb5256c1d
--- /dev/null
+++ b/scripts/cmake/jedbrown/FindPETSc.cmake
@@ -0,0 +1,346 @@
+# - Try to find PETSc
+# Once done this will define
+#
+#  PETSC_FOUND        - system has PETSc
+#  PETSC_INCLUDES     - the PETSc include directories
+#  PETSC_LIBRARIES    - Link these to use PETSc
+#  PETSC_COMPILER     - Compiler used by PETSc, helpful to find a compatible MPI
+#  PETSC_DEFINITIONS  - Compiler switches for using PETSc
+#  PETSC_MPIEXEC      - Executable for running MPI programs
+#  PETSC_VERSION      - Version string (MAJOR.MINOR.SUBMINOR)
+#
+#  Usage:
+#  find_package(PETSc COMPONENTS CXX)  - required if build --with-clanguage=C++ --with-c-support=0
+#  find_package(PETSc COMPONENTS C)    - standard behavior of checking build using a C compiler
+#  find_package(PETSc)                 - same as above
+#
+# Setting these changes the behavior of the search
+#  PETSC_DIR - directory in which PETSc resides
+#  PETSC_ARCH - build architecture
+#
+# Redistribution and use is allowed according to the terms of the BSD license.
+# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
+#
+
+cmake_policy(VERSION 3.3)
+
+set(PETSC_VALID_COMPONENTS
+  C
+  CXX)
+
+if(NOT PETSc_FIND_COMPONENTS)
+  get_property (_enabled_langs GLOBAL PROPERTY ENABLED_LANGUAGES)
+  if ("C" IN_LIST _enabled_langs)
+    set(PETSC_LANGUAGE_BINDINGS "C")
+  else ()
+    set(PETSC_LANGUAGE_BINDINGS "CXX")
+  endif ()
+else()
+  # Right now, this is designed for compatability with the --with-clanguage option, so
+  # only allow one item in the components list.
+  list(LENGTH ${PETSc_FIND_COMPONENTS} components_length)
+  if(${components_length} GREATER 1)
+    message(FATAL_ERROR "Only one component for PETSc is allowed to be specified")
+  endif()
+  # This is a stub for allowing multiple components should that time ever come. Perhaps
+  # to also test Fortran bindings?
+  foreach(component ${PETSc_FIND_COMPONENTS})
+    list(FIND PETSC_VALID_COMPONENTS ${component} component_location)
+    if(${component_location} EQUAL -1)
+      message(FATAL_ERROR "\"${component}\" is not a valid PETSc component.")
+    else()
+      list(APPEND PETSC_LANGUAGE_BINDINGS ${component})
+    endif()
+  endforeach()
+endif()
+
+function (petsc_get_version)
+  if (EXISTS "${PETSC_DIR}/include/petscversion.h")
+    file (STRINGS "${PETSC_DIR}/include/petscversion.h" vstrings REGEX "#define PETSC_VERSION_(RELEASE|MAJOR|MINOR|SUBMINOR|PATCH) ")
+    foreach (line ${vstrings})
+      string (REGEX REPLACE " +" ";" fields ${line}) # break line into three fields (the first is always "#define")
+      list (GET fields 1 var)
+      list (GET fields 2 val)
+      set (${var} ${val} PARENT_SCOPE)
+      set (${var} ${val})         # Also in local scope so we have access below
+    endforeach ()
+    if (PETSC_VERSION_RELEASE)
+      if ($(PETSC_VERSION_PATCH) GREATER 0)
+        set (PETSC_VERSION "${PETSC_VERSION_MAJOR}.${PETSC_VERSION_MINOR}.${PETSC_VERSION_SUBMINOR}p${PETSC_VERSION_PATCH}" CACHE INTERNAL "PETSc version")
+      else ()
+        set (PETSC_VERSION "${PETSC_VERSION_MAJOR}.${PETSC_VERSION_MINOR}.${PETSC_VERSION_SUBMINOR}" CACHE INTERNAL "PETSc version")
+      endif ()
+    else ()
+      # make dev version compare higher than any patch level of a released version
+      set (PETSC_VERSION "${PETSC_VERSION_MAJOR}.${PETSC_VERSION_MINOR}.${PETSC_VERSION_SUBMINOR}.99" CACHE INTERNAL "PETSc version")
+    endif ()
+  else ()
+    message (SEND_ERROR "PETSC_DIR can not be used, ${PETSC_DIR}/include/petscversion.h does not exist")
+  endif ()
+endfunction ()
+
+# Debian uses versioned paths e.g /usr/lib/petscdir/3.5/
+file (GLOB DEB_PATHS "/usr/lib/petscdir/*")
+
+find_path (PETSC_DIR include/petsc.h
+  HINTS ENV PETSC_DIR
+  PATHS
+  /usr/lib/petsc
+  # Debian paths
+  ${DEB_PATHS}
+  # Arch Linux path
+  /opt/petsc/linux-c-opt
+  # MacPorts path
+  /opt/local/lib/petsc
+  $ENV{HOME}/petsc
+  DOC "PETSc Directory")
+
+find_program (MAKE_EXECUTABLE NAMES make gmake)
+
+if (PETSC_DIR AND NOT PETSC_ARCH)
+  set (_petsc_arches
+    $ENV{PETSC_ARCH}                   # If set, use environment variable first
+    linux-gnu-c-debug linux-gnu-c-opt  # Debian defaults
+    x86_64-unknown-linux-gnu i386-unknown-linux-gnu)
+  set (petscconf "NOTFOUND" CACHE FILEPATH "Cleared" FORCE)
+  foreach (arch ${_petsc_arches})
+    if (NOT PETSC_ARCH)
+      find_path (petscconf petscconf.h
+        HINTS ${PETSC_DIR}
+        PATH_SUFFIXES ${arch}/include bmake/${arch}
+        NO_DEFAULT_PATH)
+      if (petscconf)
+        set (PETSC_ARCH "${arch}" CACHE STRING "PETSc build architecture")
+      endif (petscconf)
+    endif (NOT PETSC_ARCH)
+  endforeach (arch)
+  set (petscconf "NOTFOUND" CACHE INTERNAL "Scratch variable" FORCE)
+endif (PETSC_DIR AND NOT PETSC_ARCH)
+
+set (petsc_slaves LIBRARIES_SYS LIBRARIES_VEC LIBRARIES_MAT LIBRARIES_DM LIBRARIES_KSP LIBRARIES_SNES LIBRARIES_TS
+  INCLUDE_DIR INCLUDE_CONF)
+include (FindPackageMultipass)
+find_package_multipass (PETSc petsc_config_current
+  STATES DIR ARCH
+  DEPENDENTS INCLUDES LIBRARIES COMPILER MPIEXEC ${petsc_slaves})
+
+# Determine whether the PETSc layout is old-style (through 2.3.3) or
+# new-style (>= 3.0.0)
+if (EXISTS "${PETSC_DIR}/${PETSC_ARCH}/lib/petsc/conf/petscvariables") # > 3.5
+  set (petsc_conf_rules "${PETSC_DIR}/lib/petsc/conf/rules")
+  set (petsc_conf_variables "${PETSC_DIR}/lib/petsc/conf/variables")
+elseif (EXISTS "${PETSC_DIR}/${PETSC_ARCH}/include/petscconf.h")   # > 2.3.3
+  set (petsc_conf_rules "${PETSC_DIR}/conf/rules")
+  set (petsc_conf_variables "${PETSC_DIR}/conf/variables")
+elseif (EXISTS "${PETSC_DIR}/bmake/${PETSC_ARCH}/petscconf.h") # <= 2.3.3
+  set (petsc_conf_rules "${PETSC_DIR}/bmake/common/rules")
+  set (petsc_conf_variables "${PETSC_DIR}/bmake/common/variables")
+elseif (PETSC_DIR)
+  message (SEND_ERROR "The pair PETSC_DIR=${PETSC_DIR} PETSC_ARCH=${PETSC_ARCH} do not specify a valid PETSc installation")
+endif ()
+
+if (petsc_conf_rules AND petsc_conf_variables AND NOT petsc_config_current)
+  petsc_get_version()
+
+  # Put variables into environment since they are needed to get
+  # configuration (petscvariables) in the PETSc makefile
+  set (ENV{PETSC_DIR} "${PETSC_DIR}")
+  set (ENV{PETSC_ARCH} "${PETSC_ARCH}")
+
+  # A temporary makefile to probe the PETSc configuration
+  set (petsc_config_makefile "${PROJECT_BINARY_DIR}/Makefile.petsc")
+  file (WRITE "${petsc_config_makefile}"
+"## This file was autogenerated by FindPETSc.cmake
+# PETSC_DIR  = ${PETSC_DIR}
+# PETSC_ARCH = ${PETSC_ARCH}
+include ${petsc_conf_rules}
+include ${petsc_conf_variables}
+show :
+\t-@echo -n \${\${VARIABLE}}
+")
+
+  macro (PETSC_GET_VARIABLE name var)
+    set (${var} "NOTFOUND" CACHE INTERNAL "Cleared" FORCE)
+    execute_process (COMMAND ${MAKE_EXECUTABLE} --no-print-directory -f ${petsc_config_makefile} show VARIABLE=${name}
+      OUTPUT_VARIABLE ${var}
+      RESULT_VARIABLE petsc_return)
+  endmacro (PETSC_GET_VARIABLE)
+  petsc_get_variable (PETSC_LIB_DIR            petsc_lib_dir)
+  petsc_get_variable (PETSC_EXTERNAL_LIB_BASIC petsc_libs_external)
+  petsc_get_variable (PETSC_CCPPFLAGS          petsc_cpp_line)
+  petsc_get_variable (PETSC_INCLUDE            petsc_include)
+  petsc_get_variable (PCC                      petsc_cc)
+  petsc_get_variable (PCC_FLAGS                petsc_cc_flags)
+  petsc_get_variable (MPIEXEC                  petsc_mpiexec)
+  # We are done with the temporary Makefile, calling PETSC_GET_VARIABLE after this point is invalid!
+  file (REMOVE ${petsc_config_makefile})
+
+  include (ResolveCompilerPaths)
+  # Extract include paths and libraries from compile command line
+  resolve_includes (petsc_includes_all "${petsc_cpp_line}")
+
+  #on windows we need to make sure we're linking against the right
+  #runtime library
+  if (WIN32)
+    if (petsc_cc_flags MATCHES "-MT")
+      set(using_md False)
+      foreach(flag_var
+          CMAKE_C_FLAGS CMAKE_C_FLAGS_DEBUG CMAKE_C_FLAGS_RELEASE
+          CMAKE_C_FLAGS_MINSIZEREL CMAKE_C_FLAGS_RELWITHDEBINFO
+          CMAKE_CXX_FLAGS CMAKE_CXX_FLAGS_DEBUG CMAKE_CXX_FLAGS_RELEASE
+          CMAKE_CXX_FLAGS_MINSIZEREL CMAKE_CXX_FLAGS_RELWITHDEBINFO)
+        if(${flag_var} MATCHES "/MD")
+          set(using_md True)
+        endif(${flag_var} MATCHES "/MD")
+      endforeach(flag_var)
+      if(${using_md} MATCHES "True")
+        message(WARNING "PETSc was built with /MT, but /MD is currently set.
+ See http://www.cmake.org/Wiki/CMake_FAQ#How_can_I_build_my_MSVC_application_with_a_static_runtime.3F")
+      endif(${using_md} MATCHES "True")
+    endif (petsc_cc_flags MATCHES "-MT")
+  endif (WIN32)
+
+  include (CorrectWindowsPaths)
+  convert_cygwin_path(petsc_lib_dir)
+  message (STATUS "petsc_lib_dir ${petsc_lib_dir}")
+
+  macro (PETSC_FIND_LIBRARY suffix name)
+    set (PETSC_LIBRARY_${suffix} "NOTFOUND" CACHE INTERNAL "Cleared" FORCE) # Clear any stale value, if we got here, we need to find it again
+    if (WIN32)
+      set (libname lib${name}) #windows expects "libfoo", linux expects "foo"
+    else (WIN32)
+      set (libname ${name})
+    endif (WIN32)
+    find_library (PETSC_LIBRARY_${suffix} NAMES ${libname} HINTS ${petsc_lib_dir} NO_DEFAULT_PATH)
+    set (PETSC_LIBRARIES_${suffix} "${PETSC_LIBRARY_${suffix}}")
+    mark_as_advanced (PETSC_LIBRARY_${suffix})
+  endmacro (PETSC_FIND_LIBRARY suffix name)
+
+  # Look for petscvec first, if it doesn't exist, we must be using single-library
+  petsc_find_library (VEC petscvec)
+  if (PETSC_LIBRARY_VEC)
+    petsc_find_library (SYS  "petscsys;petsc") # libpetscsys is called libpetsc prior to 3.1 (when single-library was introduced)
+    petsc_find_library (MAT  petscmat)
+    petsc_find_library (DM   petscdm)
+    petsc_find_library (KSP  petscksp)
+    petsc_find_library (SNES petscsnes)
+    petsc_find_library (TS   petscts)
+    macro (PETSC_JOIN libs deps)
+      list (APPEND PETSC_LIBRARIES_${libs} ${PETSC_LIBRARIES_${deps}})
+    endmacro (PETSC_JOIN libs deps)
+    petsc_join (VEC  SYS)
+    petsc_join (MAT  VEC)
+    petsc_join (DM   MAT)
+    petsc_join (KSP  DM)
+    petsc_join (SNES KSP)
+    petsc_join (TS   SNES)
+    petsc_join (ALL  TS)
+  else ()
+    set (PETSC_LIBRARY_VEC "NOTFOUND" CACHE INTERNAL "Cleared" FORCE) # There is no libpetscvec
+    petsc_find_library (SINGLE petsc)
+    # Debian 9/Ubuntu 16.04 uses _real and _complex extensions when using libraries in /usr/lib/petsc.
+    if (NOT PETSC_LIBRARY_SINGLE)
+      petsc_find_library (SINGLE petsc_real)
+    endif()
+    if (NOT PETSC_LIBRARY_SINGLE)
+      petsc_find_library (SINGLE petsc_complex)
+    endif()
+    foreach (pkg SYS VEC MAT DM KSP SNES TS ALL)
+      set (PETSC_LIBRARIES_${pkg} "${PETSC_LIBRARY_SINGLE}")
+    endforeach ()
+  endif ()
+  if (PETSC_LIBRARY_TS)
+    message (STATUS "Recognized PETSc install with separate libraries for each package")
+  else ()
+    message (STATUS "Recognized PETSc install with single library for all packages")
+  endif ()
+
+  include(Check${PETSC_LANGUAGE_BINDINGS}SourceRuns)
+  macro (PETSC_TEST_RUNS includes libraries runs)
+    if (PETSC_VERSION VERSION_GREATER 3.1)
+      set (_PETSC_TSDestroy "TSDestroy(&ts)")
+    else ()
+      set (_PETSC_TSDestroy "TSDestroy(ts)")
+    endif ()
+
+    set(_PETSC_TEST_SOURCE "
+static const char help[] = \"PETSc test program.\";
+#include <petscts.h>
+int main(int argc,char *argv[]) {
+  PetscErrorCode ierr;
+  TS ts;
+
+  ierr = PetscInitialize(&argc,&argv,0,help);CHKERRQ(ierr);
+  ierr = TSCreate(PETSC_COMM_WORLD,&ts);CHKERRQ(ierr);
+  ierr = TSSetFromOptions(ts);CHKERRQ(ierr);
+  ierr = ${_PETSC_TSDestroy};CHKERRQ(ierr);
+  ierr = PetscFinalize();CHKERRQ(ierr);
+  return 0;
+}
+")
+    multipass_source_runs ("${includes}" "${libraries}" "${_PETSC_TEST_SOURCE}" ${runs} "${PETSC_LANGUAGE_BINDINGS}")
+    if (${${runs}})
+      set (PETSC_EXECUTABLE_RUNS "YES" CACHE BOOL
+        "Can the system successfully run a PETSc executable?  This variable can be manually set to \"YES\" to force CMake to accept a given PETSc configuration, but this will almost always result in a broken build.  If you change PETSC_DIR, PETSC_ARCH, or PETSC_CURRENT you would have to reset this variable." FORCE)
+    endif (${${runs}})
+  endmacro (PETSC_TEST_RUNS)
+
+
+  find_path (PETSC_INCLUDE_DIR petscts.h HINTS "${PETSC_DIR}" PATH_SUFFIXES include NO_DEFAULT_PATH)
+  find_path (PETSC_INCLUDE_CONF petscconf.h HINTS "${PETSC_DIR}" PATH_SUFFIXES "${PETSC_ARCH}/include" "bmake/${PETSC_ARCH}" NO_DEFAULT_PATH)
+  mark_as_advanced (PETSC_INCLUDE_DIR PETSC_INCLUDE_CONF)
+  set (petsc_includes_minimal ${PETSC_INCLUDE_CONF} ${PETSC_INCLUDE_DIR})
+
+  petsc_test_runs ("${petsc_includes_minimal}" "${PETSC_LIBRARIES_TS}" petsc_works_minimal)
+  if (petsc_works_minimal)
+    message (STATUS "Minimal PETSc includes and libraries work.  This probably means we are building with shared libs.")
+    set (petsc_includes_needed "${petsc_includes_minimal}")
+  else (petsc_works_minimal)     # Minimal includes fail, see if just adding full includes fixes it
+    petsc_test_runs ("${petsc_includes_all}" "${PETSC_LIBRARIES_TS}" petsc_works_allincludes)
+    if (petsc_works_allincludes) # It does, we just need all the includes (
+      message (STATUS "PETSc requires extra include paths, but links correctly with only interface libraries.  This is an unexpected configuration (but it seems to work fine).")
+      set (petsc_includes_needed ${petsc_includes_all})
+    else (petsc_works_allincludes) # We are going to need to link the external libs explicitly
+      resolve_libraries (petsc_libraries_external "${petsc_libs_external}")
+      foreach (pkg SYS VEC MAT DM KSP SNES TS ALL)
+        list (APPEND PETSC_LIBRARIES_${pkg}  ${petsc_libraries_external})
+      endforeach (pkg)
+      petsc_test_runs ("${petsc_includes_minimal}" "${PETSC_LIBRARIES_TS}" petsc_works_alllibraries)
+      if (petsc_works_alllibraries)
+         message (STATUS "PETSc only need minimal includes, but requires explicit linking to all dependencies.  This is expected when PETSc is built with static libraries.")
+        set (petsc_includes_needed ${petsc_includes_minimal})
+      else (petsc_works_alllibraries)
+        # It looks like we really need everything, should have listened to Matt
+        set (petsc_includes_needed ${petsc_includes_all})
+        petsc_test_runs ("${petsc_includes_all}" "${PETSC_LIBRARIES_TS}" petsc_works_all)
+        if (petsc_works_all) # We fail anyways
+          message (STATUS "PETSc requires extra include paths and explicit linking to all dependencies.  This probably means you have static libraries and something unexpected in PETSc headers.")
+        else (petsc_works_all) # We fail anyways
+          message (STATUS "PETSc could not be used, maybe the install is broken.")
+        endif (petsc_works_all)
+      endif (petsc_works_alllibraries)
+    endif (petsc_works_allincludes)
+  endif (petsc_works_minimal)
+
+  # We do an out-of-source build so __FILE__ will be an absolute path, hence __INSDIR__ is superfluous
+  if (${PETSC_VERSION} VERSION_LESS 3.1)
+    set (PETSC_DEFINITIONS "-D__SDIR__=\"\"" CACHE STRING "PETSc definitions" FORCE)
+  else ()
+    set (PETSC_DEFINITIONS "-D__INSDIR__=" CACHE STRING "PETSc definitions" FORCE)
+  endif ()
+  # Sometimes this can be used to assist FindMPI.cmake
+  set (PETSC_MPIEXEC ${petsc_mpiexec} CACHE FILEPATH "Executable for running PETSc MPI programs" FORCE)
+  set (PETSC_INCLUDES ${petsc_includes_needed} CACHE STRING "PETSc include path" FORCE)
+  set (PETSC_LIBRARIES ${PETSC_LIBRARIES_ALL} CACHE STRING "PETSc libraries" FORCE)
+  set (PETSC_COMPILER ${petsc_cc} CACHE FILEPATH "PETSc compiler" FORCE)
+  # Note that we have forced values for all these choices.  If you
+  # change these, you are telling the system to trust you that they
+  # work.  It is likely that you will end up with a broken build.
+  mark_as_advanced (PETSC_INCLUDES PETSC_LIBRARIES PETSC_COMPILER PETSC_DEFINITIONS PETSC_MPIEXEC PETSC_EXECUTABLE_RUNS)
+endif ()
+
+include (FindPackageHandleStandardArgs)
+find_package_handle_standard_args (PETSc
+  REQUIRED_VARS PETSC_INCLUDES PETSC_LIBRARIES PETSC_EXECUTABLE_RUNS
+  VERSION_VAR PETSC_VERSION
+  FAIL_MESSAGE "PETSc could not be found.  Be sure to set PETSC_DIR and PETSC_ARCH.")
diff --git a/scripts/cmake/jedbrown/README.md b/scripts/cmake/jedbrown/README.md
new file mode 100644
index 0000000000000000000000000000000000000000..8a11f28c18e081c20b5ba73c6e6df6ca67bfe97d
--- /dev/null
+++ b/scripts/cmake/jedbrown/README.md
@@ -0,0 +1,3 @@
+Copied the following files from https://github.com/jedbrown/cmake-modules:
+
+- FindPETSC.cmake
diff --git a/web/content/docs/devguide/getting-started/prerequisites.pandoc b/web/content/docs/devguide/getting-started/prerequisites.pandoc
index 477f64bb4c51f8994994b954b389e46d0d60ff8a..50babcb9b3edf20533d59a2f57f1e51b05720134 100644
--- a/web/content/docs/devguide/getting-started/prerequisites.pandoc
+++ b/web/content/docs/devguide/getting-started/prerequisites.pandoc
@@ -14,28 +14,28 @@ weight = 1002
 The minimum prerequisites to build OGS are:
 
 - An 64-bit operating system (Linux, Windows 7 and up, macOS)
-- Git (version control tool, at least version 1.7.x)
-- CMake (build configuration tool, at least version 3.1)
-- A compiler with [C++11](http://en.wikipedia.org/wiki/C%2B%2B11)-support
-- [Conan package manager](https://www.conan.io/) **OR** install [required libraries]({{< ref "third-party-libraries.pandoc" >}}) manually (for advanced users only!)
+- Git (version control tool, at least version {{< dataFile "versions.minimum_version.git" >}})
+- CMake (build configuration tool, at least version 3.12)
+- A compiler with [C++17](http://en.wikipedia.org/wiki/C%2B%2B17)-support
+- [Conan package manager](https://www.conan.io/) (at least version {{< dataFile "versions.minimum_version.conan" >}}) **OR** install [required libraries]({{< ref "third-party-libraries.pandoc" >}}) manually (for advanced users only!)
 
 ## Step: Install a compiler
 
 ::: {.win}
-As we use lots of features of the C++11-standard we support **Visual Studio 2015** and up. Therefore you will need at least **Windows 7** (64-bit recommended). It is perfectly fine to use the free Community Edition of Visual Studio.
+As we use lots of features of the C++17-standard we support **Visual Studio {{< dataFile "versions.minimum_version.msvc.year" >}}** and up. Therefore you will need at least **Windows 7** (64-bit recommended). It is perfectly fine to use the free Community Edition of Visual Studio.
 
-- Download and install [Visual Studio Community 2017](https://www.visualstudio.com/de/thank-you-downloading-visual-studio/?sku=Community&rel=15)
+- Download and install [Visual Studio Community](https://www.visualstudio.com)
   - Select the *workload* `Desktop Development with C++`
   - You can uncheck everything else
 - When installation finished please start Visual Studio once (when asked for credentials enter your Microsoft account or click on **Skip for now**)
 :::
 
 ::: {.linux}
-If you have a recent linux distribution you should also have a recent gcc. Please check that you have at least **gcc 6.2**:
+If you have a recent linux distribution you should also have a recent gcc. Please check that you have at least **gcc {{< dataFile "versions.minimum_version.gcc" >}}**:
 
 ```bash
 $ gcc --version
-gcc (GCC) 6.2.0
+gcc (GCC) {{< dataFile "versions.minimum_version.gcc" >}}.0
 ```
 :::
 
@@ -147,9 +147,7 @@ git config --global http.proxy http://yourproxy.example.com
 [Git LFS](https://git-lfs.github.com/) (large file storage) is a git extension dealing with large binary files such as images and is used for the documentation. You don't need to worry about anything but you need to install the extension as it is not a part of standard git.
 
 ::: {.win}
-- If you have at least Git version 2.14 you can skip the following step:
-  - Go to the [git-lfs release page](https://github.com/git-lfs/git-lfs/releases/latest) and download the file called **Windows Installer**. Install the file.
-- In the command line run: `git lfs install`
+- Git LFS is already part of your regular git installation, to enable it run: `git lfs install` in the command line
 :::
 
 ::: {.linux}
@@ -244,7 +242,7 @@ $ brew install cmake
 
 The [Conan package manager](https://www.conan.io) helps to install all required libraries in a convenient way on every platform. If you prefer you can also [install libraries manually]({{< ref "third-party-libraries.pandoc" >}}) instead.
 
-Install Conan with Python's pip:
+Install Conan (>= {{< dataFile "versions.minimum_version.conan" >}}) with Python's pip:
 
 ```bash
 pip3 install --user conan
@@ -256,5 +254,5 @@ Check on a newly opened command line if Conan was installed successfully:
 
 ```bash
 $ conan --version
-Conan version 1.12.3
+Conan version {{< dataFile "versions.minimum_version.conan" >}}
 ```
diff --git a/web/data/versions.json b/web/data/versions.json
new file mode 100644
index 0000000000000000000000000000000000000000..65efe875754357495d05384efba12578ba5258f6
--- /dev/null
+++ b/web/data/versions.json
@@ -0,0 +1,13 @@
+{
+  "minimum_version": {
+    "gcc": "7.3",
+    "clang": "3.5",
+    "msvc": {
+      "year": "2017",
+      "number": "15",
+      "toolset": "141"
+    },
+    "conan": "1.21.0",
+    "git": "2.14"
+  }
+}
diff --git a/web/layouts/shortcodes/dataFile.html b/web/layouts/shortcodes/dataFile.html
new file mode 100644
index 0000000000000000000000000000000000000000..d47c61c71a2be7278b7c8d5d967c9cebc5b19fd1
--- /dev/null
+++ b/web/layouts/shortcodes/dataFile.html
@@ -0,0 +1,9 @@
+{{- with .Get 0 -}}
+  {{- $map := split . "." }}
+  {{- $url := index $.Site.Data $map -}}
+  {{- if $url -}}
+{{- $url -}}
+  {{- else -}}
+{{- errorf "No data for key %s" . -}}
+  {{- end -}}
+{{- end -}}