From 62e9e0cbbb0c869fc59c78b81b8ba83749301fea Mon Sep 17 00:00:00 2001 From: Braden Obrzut Date: Sun, 2 Feb 2020 00:14:37 -0500 Subject: [PATCH] - Change updaterevision to a CMake script The benefit to this is fairly small, but it does mean a little less work needs to be done in the build scripts for cross compiling. The C version wasn't especially concise so it was not obviously better in any way. --- src/CMakeLists.txt | 4 +- tools/CMakeLists.txt | 1 - tools/updaterevision/CMakeLists.txt | 24 ---- tools/updaterevision/UpdateRevision.cmake | 91 +++++++++++++++ tools/updaterevision/gitinfo.h.in | 8 ++ tools/updaterevision/trustinfo.rc | 6 - tools/updaterevision/trustinfo.txt | 16 --- tools/updaterevision/updaterevision.c | 136 ---------------------- 8 files changed, 101 insertions(+), 185 deletions(-) delete mode 100644 tools/updaterevision/CMakeLists.txt create mode 100755 tools/updaterevision/UpdateRevision.cmake create mode 100644 tools/updaterevision/gitinfo.h.in delete mode 100644 tools/updaterevision/trustinfo.rc delete mode 100644 tools/updaterevision/trustinfo.txt delete mode 100644 tools/updaterevision/updaterevision.c diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 01c719de08a..292fba76016 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -426,9 +426,9 @@ endif() # Update gitinfo.h add_custom_target( revision_check ALL - COMMAND updaterevision src/gitinfo.h + COMMAND "${CMAKE_COMMAND}" -P "${CMAKE_SOURCE_DIR}/tools/updaterevision/UpdateRevision.cmake" src/gitinfo.h WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} - DEPENDS updaterevision ) +) # Libraries ZDoom needs diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt index d9d35fd5ad3..b3fed70ff39 100644 --- a/tools/CMakeLists.txt +++ b/tools/CMakeLists.txt @@ -2,7 +2,6 @@ cmake_minimum_required( VERSION 2.8.7 ) add_subdirectory( re2c ) add_subdirectory( lemon ) -add_subdirectory( updaterevision ) add_subdirectory( zipdir ) set( CROSS_EXPORTS ${CROSS_EXPORTS} PARENT_SCOPE ) diff --git a/tools/updaterevision/CMakeLists.txt b/tools/updaterevision/CMakeLists.txt deleted file mode 100644 index db99ab812e7..00000000000 --- a/tools/updaterevision/CMakeLists.txt +++ /dev/null @@ -1,24 +0,0 @@ -cmake_minimum_required( VERSION 2.8.7 ) - -if( WIN32 ) - if( MSVC_VERSION GREATER 1399 ) - # VC 8+ adds a manifest automatically to the executable. We need to - # merge ours with it. - set( MT_MERGE ON ) - else() - set( TRUSTINFO trustinfo.rc ) - endif() -else( WIN32 ) - set( TRUSTINFO "" ) -endif() - -if( NOT CMAKE_CROSSCOMPILING ) - add_executable( updaterevision updaterevision.c ${TRUSTINFO} ) - set( CROSS_EXPORTS ${CROSS_EXPORTS} updaterevision PARENT_SCOPE ) -endif() - -if( MT_MERGE ) - add_custom_command(TARGET updaterevision POST_BUILD - COMMAND mt -inputresource:$ -manifest ${CMAKE_CURRENT_SOURCE_DIR}/trustinfo.txt -outputresource:$ -nologo - COMMENT "Embedding trustinfo into updaterevision" ) -endif() diff --git a/tools/updaterevision/UpdateRevision.cmake b/tools/updaterevision/UpdateRevision.cmake new file mode 100755 index 00000000000..619a86862a4 --- /dev/null +++ b/tools/updaterevision/UpdateRevision.cmake @@ -0,0 +1,91 @@ +#!/usr/bin/cmake -P + +# UpdateRevision.cmake +# +# Public domain. This program uses git commands command to get +# various bits of repository status for a particular directory +# and writes it into a header file so that it can be used for a +# project's versioning. + +# Boilerplate to return a variable from a function. +macro(ret_var VAR) + set(${VAR} "${${VAR}}" PARENT_SCOPE) +endmacro() + +# Populate variables "Hash", "Tag", and "Timestamp" with relevant information +# from source repository. If anything goes wrong return something in "Error." +function(query_repo_info) + execute_process( + COMMAND git describe --tags --dirty=-m + RESULT_VARIABLE Error + OUTPUT_VARIABLE Tag + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE + ) + if(NOT "${Error}" STREQUAL "0") + ret_var(Error) + return() + endif() + + execute_process( + COMMAND git log -1 "--format=%ai;%H" + RESULT_VARIABLE Error + OUTPUT_VARIABLE CommitInfo + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE + ) + if(NOT "${Error}" STREQUAL "0") + ret_var(Error) + return() + endif() + + list(GET CommitInfo 0 Timestamp) + list(GET CommitInfo 1 Hash) + + ret_var(Tag) + ret_var(Timestamp) + ret_var(Hash) +endfunction() + +# Although configure_file doesn't overwrite the file if the contents are the +# same we can't easily observe that to change the status message. This +# function parses the existing file (if it exists) and puts the hash in +# variable "OldHash" +function(get_existing_hash File) + if(EXISTS "${File}") + file(STRINGS "${File}" OldHash LIMIT_COUNT 1) + if(OldHash) + string(SUBSTRING "${OldHash}" 3 -1 OldHash) + ret_var(OldHash) + endif() + endif() +endfunction() + +function(main) + if(NOT CMAKE_ARGC EQUAL 4) # cmake -P UpdateRevision.cmake + message("Usage: ${CMAKE_ARGV2} ") + return() + endif() + set(OutputFile "${CMAKE_ARGV3}") + + get_filename_component(ScriptDir "${CMAKE_SCRIPT_MODE_FILE}" DIRECTORY) + + query_repo_info() + if(NOT Hash) + message("Failed to get commit info: ${Error}") + set(Hash "0") + set(Tag "") + set(Timestamp "") + endif() + + get_existing_hash("${OutputFile}") + if(Hash STREQUAL OldHash) + message("${OutputFile} is up to date at commit ${Tag}.") + return() + endif() + + configure_file("${ScriptDir}/gitinfo.h.in" "${OutputFile}") + message("${OutputFile} updated to commit ${Tag}.") +endfunction() + +main() diff --git a/tools/updaterevision/gitinfo.h.in b/tools/updaterevision/gitinfo.h.in new file mode 100644 index 00000000000..7b8d132d301 --- /dev/null +++ b/tools/updaterevision/gitinfo.h.in @@ -0,0 +1,8 @@ +// @Hash@ +// +// This file was automatically generated by the +// updaterevision tool. Do not edit by hand. + +#define GIT_DESCRIPTION "@Tag@" +#define GIT_HASH "@Hash@" +#define GIT_TIME "@Timestamp@" diff --git a/tools/updaterevision/trustinfo.rc b/tools/updaterevision/trustinfo.rc deleted file mode 100644 index 366f9b2fd23..00000000000 --- a/tools/updaterevision/trustinfo.rc +++ /dev/null @@ -1,6 +0,0 @@ -// This resource script is for compiling with MinGW only. Visual C++ -// compilations use the manifest tool to insert the manifest instead. - -#include - -1 RT_MANIFEST "trustinfo.txt" diff --git a/tools/updaterevision/trustinfo.txt b/tools/updaterevision/trustinfo.txt deleted file mode 100644 index 2bbed9fb7b4..00000000000 --- a/tools/updaterevision/trustinfo.txt +++ /dev/null @@ -1,16 +0,0 @@ - - - - - Update svnrevision.h for the ZDoom source build process. - - - - - - - - diff --git a/tools/updaterevision/updaterevision.c b/tools/updaterevision/updaterevision.c deleted file mode 100644 index bbb6dddf3a7..00000000000 --- a/tools/updaterevision/updaterevision.c +++ /dev/null @@ -1,136 +0,0 @@ -/* updaterevision.c - * - * Public domain. This program uses git commands command to get - * various bits of repository status for a particular directory - * and writes it into a header file so that it can be used for a - * project's versioning. - */ - -#define _CRT_SECURE_NO_DEPRECATE - -#include -#include -#include -#include -#include - -#ifdef _WIN32 -#define popen _popen -#define pclose _pclose -#endif - -// Used to strip newline characters from lines read by fgets. -void stripnl(char *str) -{ - if (*str != '\0') - { - size_t len = strlen(str); - if (str[len - 1] == '\n') - { - str[len - 1] = '\0'; - } - } -} - -int main(int argc, char **argv) -{ - char vertag[128], lastlog[128], lasthash[128], *hash = NULL; - FILE *stream = NULL; - int gotrev = 0, needupdate = 1; - - vertag[0] = '\0'; - lastlog[0] = '\0'; - - if (argc != 2) - { - fprintf(stderr, "Usage: %s \n", argv[0]); - return 1; - } - - // Use git describe --tags to get a version string. If we are sitting directly - // on a tag, it returns that tag. Otherwise it returns --. - // Use git log to get the time of the latest commit in ISO 8601 format and its full hash. - stream = popen("git describe --tags --dirty=-m && git log -1 --format=%ai*%H", "r"); - - if (NULL != stream) - { - if (fgets(vertag, sizeof vertag, stream) == vertag && - fgets(lastlog, sizeof lastlog, stream) == lastlog) - { - stripnl(vertag); - stripnl(lastlog); - gotrev = 1; - } - - pclose(stream); - } - - if (gotrev) - { - hash = strchr(lastlog, '*'); - if (hash != NULL) - { - *hash = '\0'; - hash++; - } - } - if (hash == NULL) - { - fprintf(stderr, "Failed to get commit info: %s\n", strerror(errno)); - strcpy(vertag, ""); - lastlog[0] = '\0'; - lastlog[1] = '0'; - lastlog[2] = '\0'; - hash = lastlog + 1; - } - - stream = fopen (argv[1], "r"); - if (stream != NULL) - { - if (!gotrev) - { // If we didn't get a revision but the file does exist, leave it alone. - fclose (stream); - return 0; - } - // Read the revision that's in this file already. If it's the same as - // what we've got, then we don't need to modify it and can avoid rebuilding - // dependant files. - if (fgets(lasthash, sizeof lasthash, stream) == lasthash) - { - stripnl(lasthash); - if (strcmp(hash, lasthash + 3) == 0) - { - needupdate = 0; - } - } - fclose (stream); - } - - if (needupdate) - { - stream = fopen (argv[1], "w"); - if (stream == NULL) - { - return 1; - } - fprintf(stream, -"// %s\n" -"//\n" -"// This file was automatically generated by the\n" -"// updaterevision tool. Do not edit by hand.\n" -"\n" -"#define GIT_DESCRIPTION \"%s\"\n" -"#define GIT_HASH \"%s\"\n" -"#define GIT_TIME \"%s\"\n", - hash, vertag, hash, lastlog); - fclose(stream); - fprintf(stderr, "%s updated to commit %s.\n", argv[1], vertag); - } - else - { - fprintf (stderr, "%s is up to date at commit %s.\n", argv[1], vertag); - } - - return 0; -}