【问题标题】:how to include git commit-number into a c++ executable?如何将 git commit-number 包含到 C++ 可执行文件中?
【发布时间】:2011-09-25 11:15:08
【问题描述】:

我使用 git 作为我的 c++ 项目的版本跟踪器。

有时我需要重复计算,我想知道我使用的是哪个版本的程序。

将 # 的提交放入主可执行文件的好方法是什么?换一种说法。我希望程序在我运行程序时在介绍性消息中告诉我当前提交的 #。

我能想到的一种方法是从 shell 中使 c++ 程序午餐“git log”并提取提交 # 但我不确定在制作期间如何做。

(我用的是linux)

【问题讨论】:

标签: c++ git makefile


【解决方案1】:

可能最简单的方法是在您的 makefile 中添加一条规则,以生成具有当前 git 提交 ID 的 .c 文件:

gitversion.c: .git/HEAD .git/index
    echo "const char *gitversion = \"$(shell git rev-parse HEAD)\";" > $@

现在只需像往常一样将gitversion.c 添加到您的构建过程中。确保在 make clean 上将其删除,并将其添加到 .gitignore,这样它就不会意外添加到 git 存储库中。将extern const char *gitversion; 添加到某处的标题中,您就可以这样访问它。

【讨论】:

  • 1) 我对 make 或 git 不太熟悉。我尝试了快速搜索,但仍然无法理解“.git/HEAD .git/index”部分。
  • gitversion.c:后面列出的文件是它所依赖的文件。 .git 是隐藏目录; HEAD 是其中的一个文件。因此,当.git/HEAD.git/index发生变化时,使用下一行的命令重建gitversion.c:
  • 是的;请注意,这并不完全完整;最好同时引用 .git/packed-refs 和 .git/refs 下的所有文件...
  • 2) 我想我误解了 smtn。这就是我所做的: 1. 将这两行放在 Makefile 中 main.o 规则之后。 2. 包括“extern const char *gitversion;”行进入 main.cc。 3. 把 cout
  • 您需要像其他任何 .c 文件一样从链接规则中实际引用 gitversion.c。
【解决方案2】:

我在 CMakeLists.txt 中执行以下操作:

IF(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/.git)
  FIND_PACKAGE(Git)
  IF(GIT_FOUND)
    EXECUTE_PROCESS(
      COMMAND ${GIT_EXECUTABLE} rev-parse --short HEAD
      WORKING_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}"
      OUTPUT_VARIABLE "kml2maps_BUILD_VERSION"
      ERROR_QUIET
      OUTPUT_STRIP_TRAILING_WHITESPACE)
    MESSAGE( STATUS "Git version: ${kml2maps_BUILD_VERSION}" )
  ELSE(GIT_FOUND)
    SET(kml2maps_BUILD_VERSION 0)
  ENDIF(GIT_FOUND)
ENDIF(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/.git)

CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/kml2mapsVersion.h.in ${CMAKE_CURRENT_BINARY_DIR}/kml2mapsVersion.h @ONLY)

所以git rev-parse --short HEAD 的输出可以很好地构建在二进制文件中。

【讨论】:

  • 此方法假定您为每次提交手动运行 cmake。
  • 要使其正常工作,您需要定义如下内容:#define GIT_REVISION "@kml2maps_BUILD_VERSION@" in kml2mapsVersion.h.in
  • 这篇文章《CMake:在项目中使用Git Branch & Commit Details》更详细的解释了cmake的机制:xit0.org/2013/04/…
【解决方案3】:

我使用git describe 来获取使用标签或提交号的版本。这通常会给出很好的版本,例如:v0.1-1-g787c667 如果分支的尖端在 'v0.1' 标记之上有额外的提交。

我使用的 git 命令是:git describe --tags --always。我通常将它与 SCons 构建系统一起使用,并将其定义为 SConstruct 的常量相关部分:

import os, sys 
from subprocess import *

def getGitDesc():   
  return Popen('git describe --tags --always', stdout=PIPE, shell=True).stdout.read ().strip ()

GIT_DESC = getGitDesc () 
print "Building " + getGitDesc () + ".." 
env = Environment ()

# set up environment 
env.Append (CPPDEFINES = { 'GIT_DESC' : ('\\"%s\\"' % GIT_DESC) } )

# build your program
env.Program (....)

在 C 或 C++ 程序中,我现在可以将 GIT_DESC 作为字符串常量访问:

# include <iostream>

using namespace std;

int main (int argc, char ** argv) {
  cout << "Version: " << GIT_DESC << endl;
  return 42;
}

注意:git describe--abbrev=N 参数可能有助于实现独立于用户 git 配置的一致版本输出。

【讨论】:

    【解决方案4】:

    如果您使用的是 Qt,请将其放入项目的 .pro 文件中:

    win32:DEFINES += GIT_BIN='C:\\Git\\bin\\git'
    # or 'C:\\Progra~1\\Git\\bin\\git' - ymmv with putting spaces in here
    win32:DEFINES += GIT_REVISION='\\"$$system($${GIT_BIN} rev-parse --short HEAD)\\"'
    unix:DEFINES += GIT_REVISION='\\"$$system(git rev-parse --short HEAD)\\"'
    

    然后在您的代码中使用 GIT_REVISION,就像在其他答案中一样 - 它的行为类似于 const char *

    (感谢 Alexander Barthel,我从他那里得到了这个提示。)

    【讨论】:

    • 手动将-D 标志添加到编译器标志列表中会更容易:QMAKE_CXXFLAGS += -DGIT_COMMIT=\"$(shell git describe --abbrev=4 --dirty --always --tags)\"
    猜你喜欢
    • 2017-08-16
    • 2019-06-05
    • 1970-01-01
    • 1970-01-01
    • 2021-06-21
    • 1970-01-01
    • 2011-10-22
    • 2020-10-22
    • 2018-12-28
    相关资源
    最近更新 更多