From 912dbbdd77f382d90e4d8ef8ffa483037248b83a Mon Sep 17 00:00:00 2001 From: kylo252 <59826753+kylo252@users.noreply.github.com> Date: Thu, 14 Jul 2022 09:12:27 +0200 Subject: [PATCH] build: gracefully handle error in git-version #19289 - only update git-version if both of these conditions are met: - `git` command succeeds - `versiondef_git.h` would change (SHA1-diff) - else print a status/warning message also move version generation out of Lua into cmake. --- cmake/GenerateVersion.cmake | 47 +++++++++++++++++++++++++++ scripts/update_version_stamp.lua | 54 -------------------------------- src/nvim/CMakeLists.txt | 40 ++++++++--------------- 3 files changed, 60 insertions(+), 81 deletions(-) create mode 100644 cmake/GenerateVersion.cmake delete mode 100755 scripts/update_version_stamp.lua diff --git a/cmake/GenerateVersion.cmake b/cmake/GenerateVersion.cmake new file mode 100644 index 0000000000..b88b31bddd --- /dev/null +++ b/cmake/GenerateVersion.cmake @@ -0,0 +1,47 @@ +# Handle generating version from Git. +set(use_git_version 0) +if(NVIM_VERSION_MEDIUM) + message(STATUS "USING NVIM_VERSION_MEDIUM: ${NVIM_VERSION_MEDIUM}") + return() +endif() + +find_program(GIT_EXECUTABLE git) +if(NOT GIT_EXECUTABLE) + message(AUTHOR_WARNING "Skipping version-string generation (cannot find git)") + return() +endif() + +execute_process( + COMMAND git describe --first-parent --tags --always --dirty + OUTPUT_VARIABLE GIT_TAG + ERROR_VARIABLE ERR + RESULT_VARIABLE RES +) + +if("${RES}" EQUAL 1) + if(EXISTS ${OUTPUT}) + message(STATUS "Unable to extract version-string from git: keeping the last known version") + else() + # this will only be executed once since the file will get generated afterwards + message(AUTHOR_WARNING "Git tag extraction failed with: " "${ERR}") + file(WRITE "${OUTPUT}" "") + endif() + return() +endif() + +string(STRIP "${GIT_TAG}" GIT_TAG) +string(REGEX REPLACE "^v[0-9]+.[0-9]+.[0-9]+-" "" NVIM_VERSION_GIT "${GIT_TAG}") +set(NVIM_VERSION_MEDIUM + "v${NVIM_VERSION_MAJOR}.${NVIM_VERSION_MINOR}.${NVIM_VERSION_PATCH}-dev-${NVIM_VERSION_GIT}" +) +set(NVIM_VERSION_STRING "#define NVIM_VERSION_MEDIUM \"${NVIM_VERSION_MEDIUM}\"\n") +string(SHA1 CURRENT_VERSION_HASH "${NVIM_VERSION_STRING}") + +if(EXISTS ${OUTPUT}) + file(SHA1 "${OUTPUT}" NVIM_VERSION_HASH) +endif() + +if(NOT "${NVIM_VERSION_HASH}" STREQUAL "${CURRENT_VERSION_HASH}") + message(STATUS "Updating NVIM_VERSION_MEDIUM: ${NVIM_VERSION_MEDIUM}") + file(WRITE "${OUTPUT}" "${NVIM_VERSION_STRING}") +endif() diff --git a/scripts/update_version_stamp.lua b/scripts/update_version_stamp.lua deleted file mode 100755 index 0342e08f31..0000000000 --- a/scripts/update_version_stamp.lua +++ /dev/null @@ -1,54 +0,0 @@ -#!/usr/bin/env lua --- --- Script to update the Git version stamp during build. --- This is called via the custom update_version_stamp target in --- src/nvim/CMakeLists.txt. --- --- arg[1]: file in which to update the version string --- arg[2]: prefix to use always ("vX.Y.Z") - -local function die(msg) - io.stderr:write(string.format('%s: %s\n', arg[0], msg)) - -- No error, fall back to using generated "-dev" version. - os.exit(0) -end - -local function iswin() - return package.config:sub(1,1) == '\\' -end - -if #arg ~= 2 then - die(string.format("Expected two args, got %d", #arg)) -end - -local versiondeffile = arg[1] -local prefix = arg[2] - -local dev_null = iswin() and 'NUL' or '/dev/null' -local described = io.popen('git describe --first-parent --dirty 2>'..dev_null):read('*l') -if not described then - described = io.popen('git describe --first-parent --tags --always --dirty'):read('*l') -end -if not described then - io.open(versiondeffile, 'w'):write('\n') - die('git-describe failed, using empty include file.') -end - --- `git describe` annotates the most recent tagged release; for pre-release --- builds we append that to the dev version -local with_prefix = prefix -if prefix:match('-dev$') ~= nil then - with_prefix = prefix .. '+' .. described:gsub('^v%d+%.%d+%.%d+-', '') -end - --- Read existing include file. -local current = io.open(versiondeffile, 'r') -if current then - current = current:read('*l') -end - --- Write new include file, if different. -local new = '#define NVIM_VERSION_MEDIUM "'..with_prefix..'"' -if current ~= new then - io.open(versiondeffile, 'w'):write(new .. '\n') -end diff --git a/src/nvim/CMakeLists.txt b/src/nvim/CMakeLists.txt index de4af8e77b..360993de68 100755 --- a/src/nvim/CMakeLists.txt +++ b/src/nvim/CMakeLists.txt @@ -222,31 +222,17 @@ function(get_preproc_output varname iname) endif() endfunction() -# Handle generating version from Git. -set(use_git_version 0) -if(NVIM_VERSION_MEDIUM) - message(STATUS "NVIM_VERSION_MEDIUM: ${NVIM_VERSION_MEDIUM}") -elseif(EXISTS ${PROJECT_SOURCE_DIR}/.git) - find_program(GIT_EXECUTABLE git) - if(GIT_EXECUTABLE) - message(STATUS "Using NVIM_VERSION_MEDIUM from Git") - set(use_git_version 1) - else() - message(STATUS "Skipping version-string generation (cannot find git)") - endif() -endif() -if(use_git_version) - # Create a update_version_stamp target to update the version during build. - file(RELATIVE_PATH relbuild "${PROJECT_SOURCE_DIR}" "${CMAKE_BINARY_DIR}") - add_custom_target(update_version_stamp ALL - COMMAND ${LUA_PRG} scripts/update_version_stamp.lua - ${relbuild}/cmake.config/auto/versiondef_git.h - "v${NVIM_VERSION_MAJOR}.${NVIM_VERSION_MINOR}.${NVIM_VERSION_PATCH}${NVIM_VERSION_PRERELEASE}" - WORKING_DIRECTORY ${PROJECT_SOURCE_DIR} - BYPRODUCTS ${CMAKE_BINARY_DIR}/cmake.config/auto/versiondef_git.h) -else() - file(WRITE ${CMAKE_BINARY_DIR}/cmake.config/auto/versiondef_git.h "") -endif() +set(NVIM_VERSION_GIT_H ${PROJECT_BINARY_DIR}/cmake.config/auto/versiondef_git.h) +add_custom_target(update_version_stamp + COMMAND ${CMAKE_COMMAND} + -DNVIM_VERSION_MAJOR=${NVIM_VERSION_MAJOR} + -DNVIM_VERSION_MINOR=${NVIM_VERSION_MINOR} + -DNVIM_VERSION_PATCH=${NVIM_VERSION_PATCH} + -DNVIM_VERSION_PRERELEASE=${NVIM_VERSION_PRERELEASE} + -DOUTPUT=${NVIM_VERSION_GIT_H} + -P ${PROJECT_SOURCE_DIR}/cmake/GenerateVersion.cmake + WORKING_DIRECTORY ${PROJECT_SOURCE_DIR} + BYPRODUCTS ${NVIM_VERSION_GIT_H}) # NVIM_GENERATED_FOR_HEADERS: generated headers to be included in headers # NVIM_GENERATED_FOR_SOURCES: generated headers to be included in sources @@ -280,9 +266,9 @@ foreach(sfile ${NVIM_SOURCES} get_preproc_output(PREPROC_OUTPUT ${gf_i}) set(depends "${HEADER_GENERATOR}" "${sfile}") - if(use_git_version AND "${f}" STREQUAL "version.c") + if("${f}" STREQUAL "version.c") # Ensure auto/versiondef_git.h exists after "make clean". - list(APPEND depends update_version_stamp) + list(APPEND depends "${NVIM_VERSION_GIT_H}") endif() add_custom_command( OUTPUT "${gf_c_h}" "${gf_h_h}"