在不同的机器上,生成的openblas生成的lib的名字可能是这样的:
libopenblas_skylakexp-r0.3.26.dev.a
libopenblas_skylakexp-r0.3.26.dev.so
也可能是这样的:
liblapack_static_haswellp-r0.3.25.dev.a
libopenblas_haswellp-r0.3.26.dev.so
这不同的名字是如何的来的呢?
假如安装进 lib/ 中的文件是 libopenblas_skylakexp-r0.3.26.dev.a
那么这个名字是怎么获得的呢?比如其中的core架构名 skylakex
从安装入手,发生在 这个makefile文件中OpenBLAS/Makefile.install
第100行左右:
#for install static library
ifneq ($(NO_STATIC),1)
@echo Copying the static library to $(DESTDIR)$(OPENBLAS_LIBRARY_DIR)
@install -m644 $(LIBNAME) "$(DESTDIR)$(OPENBLAS_LIBRARY_DIR)"
@cd "$(DESTDIR)$(OPENBLAS_LIBRARY_DIR)" ; \
# ln -fs $(LIBNAME) $(LIBPREFIX).$(LIBSUFFIX)
endif
可以知道,被cp的文件,是以 $(LIBNAME) 给出的,安装到文件夹 "$(DESTDIR)$(OPENBLAS_LIBRARY_DIR)" 下面。
接下来需要追踪 $(LIBNAME) 这个变量的定义来源。这个名字的定义出现在 Makefile.system 中:
LIBNAME ?= $(LIBPREFIX)_$(LIBCORE)p$(REVISION).$(LIBSUFFIX)
2,分拆定义
LIBNAME ?= $(LIBPREFIX)_$(LIBCORE)p$(REVISION).$(LIBSUFFIX)
由四部分组成: LIBPREFIX LIBCORE REVISION LIBSUFFIX
先把比较直接定义的三部分找到:
其中
LIBPREFIX = lib$(LIBNAMEBASE)
即 liblapack_static;
而,
REVISION = -r$(VERSION)
,而
VERSION = 0.3.25.dev
而,
LIBSUFFIX = a
最后剩下 LIBCORE 的定义;
在不同的机器上,其定义的值并不相同,
比如在一台 Intel(R) Xeon(R) CPU E5-2650 v4 @ 2.20GHz 的服务器中,
LIBCORE=haswell,这定义在 Makefile.conf 中。
如果在一台 Genuine Intel(R) CPU 0000%@ 的服务器中,哈哈哈,这是什么cpu呢?其实是一颗测试版的 i9-10980xe cpu;
LIBCORE=skylakex,也是定义在 Makefile.conf 中。
问题在于,Makefile.conf 的内容为何不同呢?
原来 Makefile.conf 这个文件是OpenBLAS构建系统动态生成的一个文件。
3,Makefile.conf 的由来
在 Makefile.prebuild 中有一个定义:
TARGET_MAKE = Makefile.conf
而且还有如下关键代码,其余部分省去了:
./getarch 0 >> $(TARGET_MAKE)
./getarch 1 >> $(TARGET_CONF)
这便是 LIBCORE 的定义由来。
那么 getarch 这个文件是怎么来的呢?
它也是构建而来的:
getarch : getarch.c cpuid.S dummy $(CPUIDEMU)
avx512=$$(./c_check$(SCRIPTSUFFIX) - - "$(CC)" $(TARGET_FLAGS) $(CFLAGS) | grep NO_AVX512); \
rv64gv=$$(./c_check$(SCRIPTSUFFIX) - - "$(CC)" $(TARGET_FLAGS) $(CFLAGS) | grep NO_RV64GV); \
$(HOSTCC) $(HOST_CFLAGS) $(EXFLAGS) $${avx512:+-D$${avx512}} $${rv64gv:+-D$${rv64gv}} -o $(@F) getarch.c cpuid.S $(CPUIDEMU)
这个构建比较有意思,值得仔细分析一下。
特别是为何上面的那颗测试版cpu,在cat /proc/cpuinfo 中都没有得到型号,却在这里可以获得架构号。