簡體   English   中英

適用於大量處理器的 MPI 發送和接收模式

[英]MPI Send and Receive modes for large number of processors

我知道有很多關於 MPI 發送和接收的不同模式的問題和答案,但我相信我的不同,或者我根本無法將這些答案應用於我的問題。

無論如何,我的情況如下。 該代碼適用於具有潛在數千個內核的高性能集群,並被組織成一個多維網格。 在我的算法中,需要執行兩個連續的操作,我們稱它們為AB ,其中AB之前。 簡要說明如下:

A : 每個處理器都有多個緩沖區。 它必須將這些緩沖區中的每一個發送到一組特定的處理器。 對於要發送的每個緩沖區,接收處理器的集合可能不同。 發送是操作A的最后一步。

B :每個處理器從一組處理器接收一組緩沖區。 操作B將在收到所有緩沖區后處理這些緩沖區。 該操作的結果將存儲在固定位置(既不在發送緩沖區中,也不在接收緩沖區中)

還給出了以下屬性:

  • A中,每個處理器都可以計算要發送到哪些處理器,並且它還可以計算相應的標簽,以防處理器從同一個發送處理器接收到多個緩沖區(這很可能)。
  • B中,每個處理器還可以計算它將從哪些處理器接收,以及發送消息的相應標簽。
  • 每個處理器都有自己的發送緩沖區和接收緩沖區,它們是不相交的(即沒有處理器也將其發送緩沖區用作接收緩沖區,反之亦然)。
  • ABA之前和B之后的其他操作中循環執行。 我們可以確保在下一次循環迭代之前不會再次使用發送緩沖區,在那里它會填充A中的新數據,並且接收緩沖區也不會再次使用,直到下一次迭代用於接收新數據在操作B中。
  • 如果可能, AB之間的過渡應該是一個同步點,即我們要確保所有處理器同時進入B

為了發送和接收, AB都必須自己使用(嵌套)循環來發送和接收不同的緩沖區。 但是,我們不能對這些發送和接收語句的順序做出任何假設,即對於任何兩個緩沖區buf0buf1 ,我們不能保證如果某個處理器在buf0之前接收到buf1 ,那么buf0也在buf1之前發送。 請注意,此時,由於確定接收/發送處理器集的復雜性,還不能選擇使用MPI_Broadcast等組操作。

問題:我應該使用哪種發送和接收模式? 我已經閱讀了很多關於這些不同模式的不同內容,但我無法真正理解它們。 最重要的屬性是無死鎖,其次是性能。 我傾向於在A中使用 MPI_Isend( MPI_Isend()而不檢查請求狀態,並在B的循環中再次使用非阻塞MPI_IRecv() ,然后使用MPI_Waitall()確保接收到所有緩沖區(因此,也已發送所有緩沖區並且處理器已同步)。

這是正確的方法,還是我必須使用緩沖發送或完全不同的東西? 我在 MPI 方面沒有大量經驗,文檔也對我沒有太大幫助。

從您描述問題的方式來看,我認為MPI_Isend可能是A的最佳(唯一?)選項,因為它保證非阻塞,而MPI_Send可能是非阻塞的,但前提是它能夠在內部緩沖您的發送緩沖區.

然后,您應該能夠使用MPI_Barrier以便所有進程同時進入B。 但這可能會影響性能。 如果你不堅持所有進程同時進入B ,一些進程可以更快地開始接收消息。 此外,鑒於您的發送和接收緩沖區不相交,這應該是安全的。

對於B ,您可以使用MPI_IrecvMPI_Recv MPI_Irecv可能更快,因為標准MPI_Recv可能正在等待來自另一個進程的較慢發送。

無論您是否在接收端阻塞,您都應該在完成循環之前調用MPI_Waitall以確保所有發送/接收操作都已成功完成。

另外一點:您可以利用MPI_ANY_SOURCEMPI_Recv以阻塞方式接收消息並立即對它們進行操作,無論它們以什么順序到達。 但是,假設您指定在收到所有數據之前不對數據進行任何操作,這可能沒有那么有用。

最后:如這些建議中所述,如果您可以重組代碼以便只使用MPI_SSend ,您將獲得最佳性能。 在這種情況下,您將完全避免任何緩沖。 為此,您必須讓所有進程首先調用MPI_Irecv然后開始通過MPI_Ssend發送。 以這種方式重構可能並不像您想象的那么難,特別是如果,正如您所說,每個進程都可以獨立地計算出它將從誰那里接收哪些消息。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM