Environment Modules 簡明教程
1. Modules 簡介
在 Linux 超算平台上,通常會安裝有不同版本的多種編譯器和其他軟件等,如常用的編譯器有 intel 和 gnu,常用的 MPI 並行庫包括 intel mpi,openmpi,mpich2 等,而且對於同一軟件,還包含不同的版本或采用不同編譯設置得到的可執行程序和鏈接庫等。在使用這些程序時,經常需要對環境變量進行修改。並且由於程序編譯時會調用不同類型編譯器或第三庫,這時程序之間還存在着依賴關系。這使得當執行某個特定版本的程序時,環境變量的修改變得十分復雜。
Environment Modules 包是一個簡化 shell 初始化的工具,它允許用戶在使用 modulefiles 進行會話期間輕松修改其環境。每個模塊文件都包含為應用程序配置 shell 所需的信息。模塊文件可以由系統上的許多用戶共享,並且用戶可以擁有自己的集合來補充或替換共享模塊文件。
2. Modules 安裝
Modules 可直接采用源碼安裝方式,在 Modules 官網下載最新4.2.1版本的源代碼。在 Terminal 中輸入如下命令安裝 Modules 軟件
# modules 安裝目錄
INSTALL_PATH=${HOME}/opt/modules-4.2.1/
tar -xvf modules-4.2.1.tar
# 進入 modules 目錄
cd modules-4.2.1
# 安裝 modules 軟件
./configure --prefix=${INSTALL_PATH}
make
make install
在安裝完畢后我們將 modules 設置腳本添加入環境變量中。注意,modules 中包含多種 shell 設置腳本,可以根據不同情況設置。這里由於我們用的是 zsh,輸入如下命令即可
echo "souce ${HOME}/opt/modules-4.2.1/init/zsh" >> ~/.zshrc
souce ~/.zshrc
輸入如下命令,查看當前包含的模塊並加載用戶模塊
➜ ~ module avail
------------------------------------------ /usr/share/Modules/modulefiles ------------------------------------------
dot module-git module-info modules null use.own
➜ ~ module load use.own
➜ ~ module list
Currently Loaded Modulefiles:
1) use.own
此時,用戶目錄下會出現 privatemodules
文件夾,用戶可以直接在此文件夾中添加自定義模塊文件添加環境變量。
3. Modules 使用
Modules 使用包括 shell 命令和 modulefile 文件定義兩部分內容,下面將分別進行介紹。
3.1. Modules 指令
module 安裝好后,即可調用 module [command] 來查看或加載模塊,主要指令如下
➜ ~ module avail # 列出當前 module path 中的所有可用模塊文件
------------------------------------------ /usr/share/Modules/modulefiles ------------------------------------------
dot module-git module-info modules null use.own
----------------------------------------- /home/lilongxiang/privatemodules -----------------------------------------
cmake/3.8.0
➜ ~ module load cmake/3.8.0 # 加載模塊文件/類
➜ ~ module list # 顯示已經加載的模塊
Currently Loaded Modulefiles:
1) use.own 2) cmake/3.8.0
➜ ~ module unload cmake # 卸載模塊文件/類
➜ ~ module list # 顯示已經加載的模塊
Currently Loaded Modulefiles:
1) use.own
3.2. Modules 腳本內容
采用 module load 命令時,可用的模塊其實都是安裝在 module path 目錄下的 modulefile 文件。一個基本 modulefile 內容如下
#%Module -*- tcl -*-
## This is a module to access something
# 顯示 module help 主要內容
proc ModulesHelp { } {
puts stderr "This module sets up access to something"
}
# 顯示 module whatis 顯示主要內容
module-whatis "sets up access to something"
# module 加載前需要模塊類
prereq module_flag
# module 加載沖突模塊類
conflict another_module_flag
# 加載其他模塊
module load gcc
# 設置環境變量
setenv SOMEVERION 0.95
# 添加環境變量
append-path PATH /home/[user]/[somedir]/bin
append-path MANPATH /home/[user]/[somedir]/man
append-path LD_LIBRARY_PATH /home/[user]/[somedir]/lib
其中包含的設置關鍵字有以下幾個
prereq
指示加載此腳本需要預先加載的模塊名,當這些模塊沒有預先加載時,module load 此模塊會報錯;conflict
指示與此模塊沖突的其他模塊類,注意這里不僅可以添加 modulefile 文件名稱,也可添加 modulefile 所在路徑文件名,此時代表模塊和文件內所有模塊類都會產生沖突;module load
指示加載此模塊同時自動加載的模塊,注意其和prereq
命令的不同;setenv
設定環境變量;append-path
添加環境變量;
3.3. Modules 腳本配置
modulefile 文件可以按照相關功能添加到不同目錄中,下面顯示了 privatemodules 文件夾內所有 modulefile 文件
.
├── cmake
│ └── 3.8.0
├── compiler
│ └── intel
│ └── 2018.1.163
└── mpi
├── gnu
│ ├── mpich2
│ │ └── 3.2.1
│ └── openmpi
│ └── 3.1.3
├── intel
│ ├── intel_mpi
│ │ └── 2018.1.163
│ ├── mpich2
│ └── openmpi
│ └── 3.1.3
└── mpich2
調用 module avail 命令,對應顯示內容如下
➜ ~ module avail
------------------------------------------ /usr/share/Modules/modulefiles ------------------------------------------
dot module-git module-info modules null use.own
----------------------------------------- /home/lilongxiang/privatemodules -----------------------------------------
cmake/3.8.0 mpi/gnu/mpich2/3.2.1 mpi/intel/intel_mpi/2018.1.163
compiler/intel/2018.1.163 mpi/gnu/openmpi/3.1.3 mpi/intel/openmpi/3.1.3
在此用戶配置文件中,所有與 mpi 庫相關的 modulefile 文件都放在了目錄 privatemodules/mpi 內,並且根據編譯時所調用的編譯器種類分為 gnu 和 intel 兩個文件夾。
按照這種設置方法可以方便的對 modulefile 文件進行配置,在每個 modulefile 文件內添加 conflict mpi
,即可避免用戶加載不同的 mpi 配置文件,當加載多個時 module 程序會直接報錯
➜ ~ module load mpi/intel/openmpi/3.1.3
Loading mpi/intel/openmpi/3.1.3
Loading requirement: compiler/intel/2018.1.163
➜ ~ module load mpi/gnu/openmpi/3.1.3
Loading mpi/gnu/openmpi/3.1.3
ERROR: mpi/gnu/openmpi/3.1.3 cannot be loaded due to a conflict.
HINT: Might try "module unload mpi/intel/openmpi/3.1.3" first.
4. Modules 示例
4.1. Intel 編譯器環境變量設置
intel 編譯器安裝后提供了 compilervars.sh 腳本文件自動為用戶添加環境變量設置,但是這種方法不適用於 module 腳本,因為 modulefile 實際為 tcl 腳本文件,因此無法運行 shell 命令。
為了獲取 intel 腳本內 設定的環境變量,可以采用 env2 腳本來方便的直接獲取。下載 env2 腳本,運行
perl ./env2 -from bash -to modulecmd "<path to intel shell script> intel64" >> intell_module_file.log
即可在 intell_module_file.log 中查看 compilervars.sh 總定義的所有環境變量。將 intell_module_file.log 文件放置到 ~/privatemodules/compiler/intel/
路徑下,文件名用具體版本號 2018.1.163
替代,隨后便可用
module load compiler/intel/2018.1.163
命令添加 intel 編譯器環境變量。
4.2. openmpi 環境變量設置
在設置好 intel 編譯器環境后,編譯 openmpi 庫並安裝到 ${HOME}/opt/openmpi-3.1.3-intel
目錄下。
在 privatemodules/mpi/intel/openmpi/3.1.3
文件內添加
#%Module -*- tcl -*-
## This is a module to access cmake-3.8.0-rc1
proc ModulesHelp { } {
puts stderr "This module sets up access to openmpi-3.1.3 built with intel compiler"
}
module-whatis "sets up access to openmpi-3.1.3 with intel compiler"
#prereq intel_2018
conflict mpi
module load compiler/intel/2018.1.163
setenv SOMEVERION 3.1.3
append-path PATH ${HOME}/opt/openmpi-3.1.3-intel/bin
append-path LD_LIBRARY_PATH ${HOME}/opt/openmpi-3.1.3-intel/lib
即可通過命令 module load mpi/intel/openmpi/3.1.3
來加載編譯后的 openmpi 環境。