能否通过静态库(.lib)获取调用它的可执行文件(.exe)的编译日期?
可行性与实现方案
该需求完全可实现,目前有几种成熟的实现路径,可根据你的静态库适用场景选择:
方案1:提供初始化接口让调用方传入编译信息(优先推荐,跨平台兼容)
这是最适合商用静态库的方案,无平台依赖,稳定性拉满,接入成本极低。
你可以在静态库的公开头文件中封装辅助宏,让调用方的编译上下文自动展开__DATE__等宏后传入静态库即可:
// 你的静态库公开头文件 my_lib.h // 初始化接口声明 void my_lib_init(const char* exe_compile_date, const char* exe_compile_time); // 封装调用宏,用户不需要手动填写参数 #define MY_LIB_AUTO_INIT() my_lib_init(__DATE__, __TIME__)
调用方只需要在自身代码的初始化位置执行MY_LIB_AUTO_INIT(),__DATE__会在调用方的预处理阶段展开为exe的编译日期,直接传递到静态库内部存储使用即可。
优势:全平台兼容,不会受编译配置、加壳等操作影响,出现问题的概率极低
方案2:运行时读取PE头时间戳(仅Windows平台,无接入成本)
Windows下的EXE属于PE格式文件,文件头默认存储了链接生成时的时间戳,你可以在静态库内部直接读取当前进程的EXE文件头获取该信息:
- 调用
GetModuleHandle(NULL)获取当前进程EXE的模块基地址 - 解析基地址指向的PE结构,读取
IMAGE_NT_HEADERS.FileHeader.TimeDateStamp字段,该值为Unix时间戳格式,可直接转换为可读的日期时间
优势:不需要调用方做任何代码修改,零接入成本;劣势:仅支持Windows平台,EXE被加壳、手动修改PE头时会返回错误结果
方案3:约定外部符号让调用方链接时注入
你可以在静态库内部声明一个未定义的外部字符串变量:
// 静态库内部代码 extern const char* g_exe_build_date;
然后在接入文档中要求调用方在自己的任意代码文件中添加一行定义:
const char* g_exe_build_date = __DATE__;
链接时链接器会自动将EXE中定义的该符号与静态库的引用关联,你可以在静态库中直接读取该变量的值。
优势:不需要额外调用初始化接口;劣势:调用方未按要求定义符号时会直接报链接错误,需要严格约定接入规则
内容的提问来源于stack exchange,提问作者Oleg Korzhukov
相关产品推荐
相关产品推荐

