Bất kỳ đề xuất nào cho các khung kiểm thử đơn vị tương thích với mã / thư viện sử dụng MPI?


13

Thông thường, tôi viết mã nối tiếp và khi tôi làm, tôi viết các bài kiểm tra đơn vị với một số khung kiểm tra kiểu xUnit (MATLAB xUnit, PyUnit / mũi hoặc khung kiểm tra C ++ của Google).

Dựa trên một tìm kiếm đáng chú ý của Google, tôi chưa thấy nhiều về cách kiểm tra mã đơn vị học viên sử dụng MPI. Có thực hành tốt nhất cho điều đó?

So với Chiến lược để thử nghiệm đơn vị và phát triển dựa trên thử nghiệm , tôi đang tìm câu trả lời liên quan đến phần mềm nào tôi nên sử dụng cho khung thử nghiệm (nếu có tồn tại - câu trả lời rất có thể là "cuộn mã của riêng bạn", trong đó ví dụ trường hợp của mã thử nghiệm tùy chỉnh sẽ hữu ích).

Hầu hết những gì tôi muốn kiểm tra là các đánh giá chức năng bên tay phải và các thói quen lắp ráp ma trận Jacobian cho các bước thời gian sẽ được tích hợp các PDE bán rời rạc. Tôi sẽ sử dụng PETSc, vì vậy nếu có bất cứ thứ gì cụ thể về PETSc, điều đó sẽ hữu ích ngoài các khung kiểm tra tổng quát hơn.

Chỉnh sửa làm rõ:

Một ví dụ sẽ là ${PETSC_DIR}/src/ts/examples/tutorials/ex2.c, nơi tôi muốn kiểm tra một cái gì đó như RHSFunction(đánh giá chức năng bên tay phải) vàRHSJacobian(một đánh giá ma trận Jacobian). Tôi sẽ thử nghiệm các giá trị đã biết cho ma trận Jacobian bên phải và lắp ráp; Tôi có thể có được các giá trị này một cách phân tích cho một số trường hợp vấn đề đơn giản. Các hàm này là các hàm dành riêng cho ứng dụng sẽ không thực hiện bất kỳ hàm cấp ứng dụng nào khác, nhưng chúng có thể gọi MPI nếu việc lắp ráp vectơ hoặc ma trận được thực hiện trong hàm (như trong ví dụ PETSc được liên kết ở trên). Nếu tôi viết các hàm chỉ tính các phần của vectơ hoặc ma trận cục bộ cho bộ xử lý, tôi sẽ muốn kiểm tra phiên bản lắp ráp toàn cầu nếu có thể bởi vì, mới đối với lập trình song song, tôi sẽ nghĩ trực quan hơn về vectơ toàn cầu và toàn cầu ma trận. Các thử nghiệm này sẽ được chạy trên các kích cỡ vấn đề nhỏ và số lượng nhỏ bộ xử lý.

Tôi có thể nghĩ ra một vài chiến lược để làm điều này:

  • Một chiến lược có thể sẽ không hoạt động tốt, dựa trên các tìm kiếm của Google mà tôi đã thực hiện về chủ đề này, sẽ là xây dựng một đầu ra đã biết, tìm ra lỗi tương đối / tuyệt đối song song và sau đó thực hiện các so sánh ngây thơ. Đầu ra có thể sẽ bị cắt xén - bất kỳ ai đã viết chương trình "Xin chào, thế giới" với MPI đều biết tại sao - điều này hạn chế tiện ích khi thực hiện kiểm tra đơn vị. ( Đây là động lực để đặt câu hỏi. ) Dường như cũng có một số khó khăn tiềm tàng trong việc gọi khung kiểm tra đơn vị.
  • Viết đầu ra vào tệp (ví dụ như trong PETSc, bằng cách sử dụng VecViewMatView) và so sánh với đầu ra đã biết với một cái gì đó như ndiffhoặc numdiff. Cảm giác ruột của tôi với phương pháp này từ kinh nghiệm trước đây khi thực hiện kiểm tra đơn vị với so sánh tệp là nó sẽ rất khó và nó sẽ yêu cầu một số bộ lọc. Tuy nhiên, phương pháp này có vẻ như là tuyệt vời để kiểm tra hồi quy, bởi vì tôi có thể thay thế các tiện ích ở trên bằng một đơn giản diffvà không phải lo lắng về việc khớp các định dạng văn bản. Tôi đã tập hợp rằng chiến lược này ít nhiều là những gì WolfgangBangerth và andybauer đang đề xuất. PETSc cũng xuất hiện để sử dụng một cách tiếp cận tương tự cho một số thử nghiệm mà nó thực hiện.
  • Sử dụng khung kiểm tra đơn vị, thu thập mọi thứ vào bộ xử lý với MPI xếp hạng 0 và yêu cầu nó chỉ thực hiện kiểm tra đơn vị nếu xếp hạng bộ xử lý là 0. Tôi có thể làm điều gì đó tương tự với các chỉ tiêu (có thể dễ dàng hơn như vậy), mặc dù việc đánh đổi là bất kỳ lỗi nào được trả về sẽ cho tôi biết rằng tôi có vấn đề trong tính toán của mình, nhưng không phải là yếu tố nào bị lỗi. Sau đó, tôi không cần phải lo lắng về bất kỳ đầu ra thử nghiệm đơn vị nào bị cắt xén; Tôi chỉ cần lo lắng về việc gọi khung kiểm tra đơn vị chính xác. PETSc dường như sử dụng các so sánh thông thường trong các chương trình ví dụ của mình khi có các giải pháp chính xác, nhưng nó không sử dụng khung kiểm tra đơn vị khi thực hiện các so sánh đó (cũng không nhất thiết phải như vậy).

Tôi chỉ quen thuộc với các bộ thử nghiệm nội bộ, vì vậy tôi không thể đề xuất bất cứ điều gì. Điều đó đang được nói, không có bộ thử nghiệm nào trong số này cho phép bạn chỉ định cách chạy tệp thực thi bạn tạo? Nếu họ làm như vậy, nó sẽ là tầm thường để xây dựng các bài kiểm tra hoạt động cho các chương trình MPI.
Bill Barth

Họ nên. Trong bất kỳ ngôn ngữ được biên dịch nào, nó chỉ là một tệp thực thi, do đó, sẽ không có vấn đề gì khi sử dụng mpiexecđể chạy nó và bao gồm các cuộc gọi như PETScInitialize/ PETScFinalizetrong mã thiết lập / mã xé. (Có lẽ, nếu tôi không sử dụng PETSc, tôi sẽ thay thế các cuộc gọi đó bằng các tương tự MPI_Init/ MPI_Finalize, tùy thuộc vào các thư viện tôi đang sử dụng.) Khung thử nghiệm của Google là một bản phát hành dựa trên nguồn, do đó biên dịch nó cùng với mã I viết cũng không phải là một vấn đề.
Geoff Oxberry

Mô tả vấn đề của bạn gợi ý cho tôi rằng bạn quan tâm đến việc sử dụng khung kiểm thử đơn vị để chạy thử nghiệm tích hợp / hồi quy. Không có gì sai với điều đó, nhưng bạn có thể muốn làm rõ câu hỏi của mình hơn một chút. Tôi nghĩ rằng nếu bạn hỏi một chuyên gia kiểm thử đơn vị cách viết bài kiểm tra đơn vị cho mã khoa học của bạn, họ sẽ bảo bạn viết bài kiểm tra theo cách mô đun. Đó là, hầu hết các bài kiểm tra của bạn sẽ không có các cuộc gọi MPI thích hợp trong đó.
Aron Ahmadia

Hãy để tôi cụ thể hơn. Một cái gì đó tôi muốn kiểm tra một vấn đề nhỏ với một số lượng nhỏ bộ xử lý (giả sử, 1-4) sẽ là liệu ma trận Jacobian được lắp ráp của tôi có thực sự dẫn đến Jacobian toàn cầu phù hợp hay không. Tôi cũng muốn kiểm tra chức năng bên tay phải của mình so với bên phải toàn cầu đã biết. Mỗi thử nghiệm như vậy vẫn chỉ nên thực hiện một chức năng duy nhất trong ứng dụng (ví dụ, trong PETSc, thử nghiệm RHSFunctionRHSJacobiantrong ${PETSC_DIR}/src/ts/examples/tutorials/ex.2) một cách riêng lẻ .
Geoff Oxberry

Tôi không nghĩ rằng một khung hiện đang tồn tại sẽ giúp bạn làm những gì bạn muốn. Chúng tôi đã xoay xở để làm một vài điều cho chúng tôi trong PyClaw, (và Lisandro đã sử dụng nó trong mpi4py và petc4py). Bạn đã xem xét khung thử nghiệm trong mpich chưa?
Aron Ahmadia

Câu trả lời:


8

Tôi là một người dùng hạnh phúc của GoogleTest với mã MPI C ++ trong môi trường xây dựng CMake / CTest:

  • CMake tự động cài đặt / liên kết googletest từ svn!
  • thêm bài kiểm tra là một lót!
  • viết các bài kiểm tra là dễ dàng! (và google giả rất mạnh mẽ!)
  • CTest có thể truyền tham số dòng lệnh cho các thử nghiệm của bạn và xuất dữ liệu sang CDash!

Đây là cách nó hoạt động. Một loạt các bài kiểm tra đơn vị yêu cầu mpi được ghi vào một số my_mpi_test.cpptệp trông như thế này:

#include <gtest/gtest.h>
#include <boost/mpi.h>

/// Most testing libraries allow to define main yourself to override initialization.
int main(int argc, char* argv[]) {
    ::testing::InitGoogleTest(&argc, argv);  /// Set gtest environment
    mpi::environment env(argc, argv);  /// Set mpi environment
    return RUN_ALL_TESTS();  /// Execute all gtest tests
}

TEST(test_batch_name, test_name) {  /// Then you can create tests as usual,
  using namespace mpi;
  communicator world;  /// and use MPI inside your tests.
  /* ... test stuff here ... */
}

CMakeLists.txt bổ sung bài kiểm tra này là:

add_mpi_test(my_mpi 2)  # Uses 2 MPI processes

nơi add_mpi_testkết thúc CMake add_testbên trong CMakeLists.txt gốc của tôi:

function(add_mpi_test name no_mpi_proc)
  include_directories(${MY_TESTING_INCLUDES})
      # My test are all called name_test.cpp
      add_executable(${name} ${name}_test.cpp)
      add_dependencies(${name} googletest)
  # Make sure to link MPI here too:
  target_link_libraries(${name} ${MY_TESTING_LIBS})
  set(test_parameters ${MPIEXEC_NUMPROC_FLAG} ${no_mpi_proc} "./${name}")
      add_test(NAME ${name} COMMAND ${MPIEXEC} ${test_parameters})
endfunction(add_mpi_test)

Phần cuối cùng này không cần thiết nhưng cho phép bạn dễ dàng thêm các bài kiểm tra mpi trong một dòng. Sau đó, bạn có thể quyết định xem bạn có muốn mã hóa số lượng các quy trình MPI cho mỗi thử nghiệm hay đọc nó thông qua một tham số dòng lệnh để ctest.


4

Có một số gói phần mềm hỗ trợ MPI sử dụng bộ công cụ CMake để thử nghiệm. Những thứ mà tôi có thể nghĩ ra khỏi đỉnh đầu là Trilinos, VTK và ParaView. Tôi nghĩ rằng bạn không muốn cho rằng các nhu cầu thực thi phải được khởi chạy với mpirun và / hoặc mpiexec. CMake đã hỗ trợ chỉ định cách khởi chạy chính xác tệp thực thi cùng với các tùy chọn khác nhau, chẳng hạn như số lượng quy trình tối đa để sử dụng và trước và sau cờ, nếu cần.

Bạn có thể muốn xem phần Trang web HPC của bảng điều khiển ParaView nơi các bài kiểm tra được chạy trên nhiều siêu máy tính NERSC và Argonne. Chôn trong đó cũng có hầu hết các cài đặt mà bạn cần chỉ định để làm cho nó hoạt động trên các máy đó.

Để tham khảo, bảng điều khiển Trilinos có rất nhiều gói được liệt kê và với tôi là khá ấn tượng trong tổ chức của nó.

Tiết lộ đầy đủ: Tôi là nhân viên của Kitware và CMake là một trong những dự án nguồn mở mà Kitware có liên quan.


Cảm ơn câu trả lời! Tôi đã xem CTest và không tìm thấy bất kỳ tài liệu nào ngoài một mô tả giống như trang trên trang web KitWare. Bạn có thể giới thiệu bất kỳ hướng dẫn miễn phí có sẵn?
Geoff Oxberry

Có rất nhiều thông tin trên wiki CMake . Có một loạt các hướng dẫn cho CMake, CTest và CPack ở đó. Tôi tìm thấy hầu hết các câu trả lời của mình cho các ứng dụng đó trên Stack Overflow .
andybauer

andybauer - Cảm ơn câu trả lời. Bạn có phiền khi chỉnh sửa câu trả lời của mình và tiết lộ mối liên hệ của bạn với KitWare không?
Aron Ahmadia

3

Chúng tôi chỉ đơn giản cuộn mã của riêng mình trong deal.II - về bản chất, chúng tôi nói với khung để thực hiện các thử nghiệm bằng cách sử dụng mpirun -np .... Trước đây chúng tôi chỉ sử dụng sơ đồ thử nghiệm dựa trên Makefile (biên dịch, liên kết, thực hiện kiểm tra, sau đó so sánh đầu ra với một đầu ra đã được lưu trước đó) và bạn có thể tìm thấy ở đây:

và đối với bối cảnh, các mục tiêu không phải MPI có ở đây:

Chúng tôi đang viết lại mọi thứ bằng CMake / CTest, với sự phát triển hiện tại ở đây:


Wolfgang, cảm ơn vì câu trả lời! PETSc dường như làm một cái gì đó tương tự.
Geoff Oxberry

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.