1、配置PVM
並行計算機(pvm)是用於網絡並行計算機上的軟件工具。設計它的目的是將異構的計算機網絡連接起來,使它使用起來就像一組分布式的並行處理器。
PVM支持多種並行計算模型,用戶使用PVM提供的函數庫可進行並行程序或分布式程序的設計工作,使用傳統的C語言和Fortran語言。系統提供了一組便於使用的通信原語,可實現一個任務向其它任務發消息,向多個任務發消息,以及阻塞和無阻塞收發消息等功能,用戶編程與網絡接口分離。
1)環境
PVM_ROOT=/usr/lib/pvm3為配置根目錄
PVM_ARCH=LINUX為配置計算機類型,包括unix
deepfuture-lx@deepfuture-lx-desktop:/usr/lib/jvm$ sudo gedit /etc/environment
PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/lib/jvm/java-6-sun/bin"
CLASSPATH=.:/usr/lib/jvm/java-6-sun/lib
JAVA_HOME=/usr/lib/jvm/java-6-sun
PVM_ROOT=/usr/lib/pvm3
PVM_ARCH=LINUX
2) PVM環境中的二進制程序的目錄和需要使用的用戶名
二進制程序目錄名默認為$PVM_ROOT/bin/$PVM_ARCH
ep為二進制程序目錄名,lo為使用非登錄PVM環境用戶的用戶名,deepfuture-laptop為主機名,&主機名表示PVM環境不自動增加這些主機
例如:
deepfuture@deepfuture-laptop:/usr/lib/pvm3$ sudo gedit hostfile
deepfuture-laptop
&deepfuture-javaeye
&deepfuture-lx lo=deepfuture
ep=/home/deepfuture/private/mytest/pvmtest/
3) 列出希望使用的所有主機
.rhosts文件
deepfuture-laptop
4)啟動pvmd程序
deepfuture@deepfuture-laptop:/usr/lib/pvm3$ pvmd hostfile &或者
deepfuture@deepfuture-laptop:/usr/lib/pvm3$ pvmd &
5)通常程序(二進制文件)的缺省目錄為:
$HOME/pvm3/bin/
6)啟動
deepfuture@deepfuture-laptop:/usr/lib/pvm3$ pvm
pvmd already running.
pvm> quit
quit
如果啟動失敗,則清除臨時文件
deepfuture@deepfuture-laptop:/usr/lib/pvm3$ sudo rm -f /tmp/pvm*.*
7)運行程序,testpro為程序名
$testpro
或
pvm>spawn -> testpro
安裝完PVM以後,還需要編輯/ect/hosts文件,來列出你要加入的所有主機名及其對應的IP地址,以便在用add命令來加入主機時,PVM可以根據主機名來尋找相應的IP,從而確定相應的主機。基本格式如下:
hostname1 10.30.13.58(numeric IP)
hostname2 10.30.13.62
… …. ….
每行一個主機。
將激活的消息緩沖區的內容放入一個預定類型的數組中
NAME
pvm_unpack - Unpack the active message buffer into arrays of prescribed data type.
SYNOPSIS
· Cint info = pvm_unpackf( const char *fmt, ... )
· int info = pvm_upkbyte( char *xp, int nitem, int stride)
· int info = pvm_upkcplx( float *cp, int nitem, int stride)
· int info = pvm_upkdcplx( double *zp, int nitem, int stride)
· int info = pvm_upkdouble( double *dp, int nitem, int stride)
· int info = pvm_upkfloat( float *fp, int nitem, int stride)
· int info = pvm_upkint( int *ip, int nitem, int stride)
· int info = pvm_upkuint( unsigned int *ip, int nitem, int stride )
· int info = pvm_upkushort( unsigned short *ip, int nitem, int stride )
· int info = pvm_upkulong( unsigned long *ip, int nitem, int stride )
· int info = pvm_upklong( long *ip, int nitem, int stride)
· int info = pvm_upkshort( short *jp, int nitem, int stride)
· int info = pvm_upkstr( char *sp )
· PVM是一個在網絡上的虛擬並行機系統的軟件包。它允許將網絡上基於UNIX操作系統的並行機和單處理機的集合當成一台單一的“並行虛擬機”來使用。 2.1 PVM的產生和發展 PVM的開發最早開始於1989年夏天,目前它的開發隊伍包括美國橡樹嶺國家實驗室(ORNL)、Tennessee大學、Emory大學以及CMU等單 位,並得到美國能源部、國家科學基金以及田納西州的資助。PVM是一套並行計算工具軟件,支持多種體系結構的計算機,象工作站、並行機以及向量機等,通過 網絡將它們連起來,給用戶提供一個功能強大的分布存儲計算機系統。PVM支持C和Fortran兩種語言,目前已發展到3.4版,由於它是免費的,因此使 用范圍非常廣泛。 2.2 PVM的特點 PVM支持用戶采用消息傳遞方式編寫並行程序,計算以任務(task)為單位,一個任務就是一個UNIX進程,每個任務都有一個taskid來標識(不同 於進程號)。PVM支持在虛擬機中自動加載任務運行,任務間可以相互通訊以及同步。在PVM系統中,一個任務被加載到哪個結點上去運行,一般來說,對用戶 是透明的(PVM允許用戶指定任務被加載的結點),這樣就方便了用戶編寫並行程序。 歸結起來,PVM的特點有如下幾點: PVM系統支持多用戶及多任務運行,多個用戶可將系統配置成相互重疊的虛擬機,每個用戶可同時執行多個應用程序。 易於編程。PVM支持多種並行計算模型,用戶使用PVM提供的函數庫可進行並行程序或分布式程序的設計工作,使用傳統的C語言和Fortran語言。 系統提供了一組便於使用的通信原語,可實現一個任務向其它任務發消息,向多個任務發消息,以及阻塞和無阻塞收發消息等功能,用戶編程與網絡接口分離。系統 還實現了通信緩沖區的動態管理機制,每個消息所需的緩沖區由PVM運行時動態申請,消息長度只受結點上可用存儲空間的限制。 PVM提出了進程組的概念,可以把一些進程組成一個進程組,一個進程可屬於多個進程組,而且可以在執行時動態改變。 支持異構計算機聯網構成並行虛擬計算機系統且易於安裝、配置。PVM支持的異構性分為三層:機器層、應用層和網絡層。也就是說,PVM允許應用任務充分利 用網絡中適於求解問題的硬件結構;PVM處理所有需要的數據轉換任務;PVM允許虛擬機內的多個機器用不同的網絡(FDDI,Token RING和Ethernet等)相連。 具有容錯功能,當發現一個結點出故障時,PVM會自動將之從虛擬機中刪除。 結構緊湊。整個系統只占3M左右的空間,並且該軟件系統是免費提供的
示例:
1、主進程 testpvm1,發送字符串,接收大寫化的字符串
C代碼 收藏代碼
#include "pvm3.h"
#include
int main(int argc,char *argv[]){
int RetCode,MessageId;
int PTid,Tid;
char Message[100];
char Result[100];
printf("testpvm1 get ptid.....\n");
PTid=pvm_mytid();//返回調用進程的任務標識符
if (PTid==PvmSysErr) perror("pvm_mytid() error:PvmSysErr\n");
printf("spawn testpvm2.....\n");
//深未來技術 deepfuture.iteye.com
RetCode=pvm_spawn("testpvm2",NULL,PvmTaskHost,"deepfuture-laptop",1,&Tid);
//啟動一個新的PVM子進程testpvm2,用來接收和處理Message消息,轉化為大寫,Tid為新的任務標識
if (RetCode==1){
MessageId=1;//指明當前消息
strcpy(Message,"deepfuture.iteye.com");
pvm_initsend(PvmDataDefault);//初始化消息緩沖區
pvm_pkstr(Message);//對變量Message的內容進行打包
pvm_send(Tid,MessageId);//將消息緩沖區的消息發送,MessageId簡單指明正在發送的消息
pvm_recv(Tid,MessageId);//接收消息
pvm_upkstr(Result);//將消息緩沖區的接收到的內容放到一個數組中。
printf("send:%s\n",Message);
printf("recv:%s\n",Result);
pvm_exit();
return 0;
}
else{
printf("不能啟動新進程\n");
pvm_exit();
return 1;
}
}
2、從進程 testpvm2,將字符串轉化為大寫,然後返回給主進程
C代碼 收藏代碼
#include "pvm3.h"
#include
int main(int argc,char *argv[]){
int RetCode,MessageId;
int PTid;
char Message[100];
char myc[100];
int i=0;
printf("testpvm2 get ptid.....\n");
PTid=pvm_parent();//返回調用進程的任務標識符
if (PTid==PvmNoParent) perror("PvmNoParent error\n");
else if (PTid==PvmSysErr) perror("PvmSysErr error\n");
printf("testpvm2 run.....\n");
MessageId=1;//指明當前消息
pvm_recv(PTid,MessageId);//接收消息
//深未來技術 deepfuture.iteye.com
pvm_upkstr(Message);//對變量Message的內容進行解包
while (Message[i]!='\0'){ //將小寫轉化成大寫
if (islower(Message[i]))
myc[i]=toupper(Message[i]);
else
myc[i]=Message[i];
i++;
}
myc[i]='\0';
pvm_initsend(PvmDataDefault);//初始化消息緩沖區
pvm_pkstr(myc);//對變量Message的內容進行打包
pvm_send(PTid,MessageId);//將消息緩沖區的消息發送,MessageId簡單指明正在發送的消息
pvm_exit();
return 0;
}
3、makefile
深未來技術 deepfuture.iteye.com
Makefile代碼 收藏代碼
testpvm:testpvm1 testpvm2
sudo cp /home/deepfuture/private/mytest/pvmtest/testpvm1 /usr/lib/pvm3/bin/LINUX/testpvm1
sudo cp /home/deepfuture/private/mytest/pvmtest/testpvm2 /usr/lib/pvm3/bin/LINUX/testpvm2
testpvm1:
gcc -o /home/deepfuture/private/mytest/pvmtest/testpvm1 -lpvm3 /home/deepfuture/private/mytest/testpvm1.c
testpvm2:
gcc -o /home/deepfuture/private/mytest/pvmtest/testpvm2 -lpvm3 /home/deepfuture/private/mytest/testpvm2.c
clean:
rm /home/deepfuture/private/mytest/pvmtest/testpvm*
sudo rm /usr/lib/pvm3/bin/LINUX/testpvm*
4、二進制文件存放目錄 為
$PVM_ROOT/bin/$PVM_ARCH
本機為/usr/lib/pvm3/bin/LINUX/
5、啟動pvmd
pvmd &
6、運行testpvm1
deepfuture@deepfuture-laptop:/usr/lib/pvm3/bin/LINUX$ ./testpvm1
testpvm1 get ptid.....
spawn testpvm2.....
send:deepfuture.iteye.com
recv:DEEPFUTURE.iteye.com
7、在pvm控制台運行testvpm1
deepfuture@deepfuture-laptop:/usr/lib/pvm3/bin/LINUX$ pvm
pvmd already running.
pvm> spawn -> testpvm1
spawn -> testpvm1
[1]
1 successful
t40042
pvm> [1:t40043] testpvm2 get ptid.....
[1:t40043] testpvm2 run.....
[1:t40042] testpvm1 get ptid.....
[1:t40042] spawn testpvm2.....
[1:t40042] send:deepfuture.iteye.com
[1:t40042] recv:DEEPFUTURE.iteye.com
[1:t40042] EOF
[1:t40043] EOF
[1] finished
8、ubuntu使用新立得安裝pvm3、libpvm3、pvm-dev
PVM安裝調試及應用程序編譯鏈接測試
說明:
1.以兩台機器為例,假定所用機器名為pvm01(202.113.12.151)和pvm02(202.113.12.152)。要求網絡工作正常。
2.運行並行程序需要在各個結點機上有相同的用戶名和密碼,並有相應的配置。這裡我們假定用戶名為pvmgroup,密碼pvmgroup。
3.例子程序為Master-Slave並行程序,用來計算Pi值,同時做一些相應的統計。dtiming為Master程 序,dtiming_slave為slave程序,Makefile.aimk是PVM程序編譯與鏈接程序aimk所使用的文件,功能與Makefile 文件相同。
一、運行環境配置與調試
1.修改/etc/hosts文件。
添加
202.113.12.151 pvm01
202.113.12.152 pvm02
2.如果是csh,修改(創建)/home/pvmgroup/.cshrc文件
setenv PVM_ROOT /usr/share/pvm3
setenv PVM_ARCH LINUX
setenv PATH /usr/share/pvm3/lib:./$PATH
如果是bash,則修改.bash_profile
# Get the aliases and functions
if [ -f ~/.bashrc ]; then
. ~/.bashrc
fi
# User specific environment and startup programs
PATH=$PATH:$HOME/bin:/usr/share/pvm3/lib
BASH_ENV=$HOME/.bashrc
USERNAME=""
PVM_ROOT=/usr/share/pvm3
PVM_ARCH=LINUX
export USERNAME BASH_ENV PATH PVM_ROOT PVM_ARCH
3.修改(創建)/home/pvmgroup/.rhosts文件。
pvm01 pvmgroup
pvm02 pvmgroup
4.調試
$ pvm
pvm> add pvm01
add pvm01
1 successful
HOST DTID
pvm01 80000
pvm> halt
halt
Terminated
如果各個結點都正確配置屏幕將有如上輸出,其中斜體為用戶輸入。如果配置有誤,將報相應錯。
二、PVM應用程序的編譯、鏈接與運行
1.創建目錄/home/pvmgroup/pvm3/bin/LINUX。(編譯好的程序要放到這裡)
2.COPY源程序及Makefile.aimk到/home/pvmgroup/pvm3/bin/LINUX目錄下。
3.$ cd /home/pvmgroup/pvm3/bin/LINUX
$ ./aimk
4.將生成的可執行文件FTP到各結點機的相同目錄下,並增加可執行屬性。
或者在每個結點機上都編譯、鏈接一遍。
如果是異構結點機,必須重新編譯。
5.啟動PVM,運行程序,步驟及正常運行結果如下:
$ pvm
pvm> add pvm01
add pvm01
1 successful
HOST DTID
pvm01 80000
pvm> quit
quit
Console: exit handler called
pvmd still running.
$ ./dtiming
i'm t40002
there has 2 machines!
slave 0 is task t80001 ok,send parameter to task 0
slave 1 is task t40003 ok,send parameter to task 1
The start time is:1026871885
task 0 finished! return is 0.8472130900904784
the time is:11
task 1 finished! return is 0.9270373444467532
the time is:0
the total time is:11
result is 3.1415926928720199
$
其中斜體為用戶輸入,其余為系統輸出。機器不同,輸出的結果也會有所不同。