// Version: $Id: d303a1d1e35238b5fa469bda67dca48f2c69bbce $ // // // Commentary: // // // Change Log: // // // Code: #pragma once #include #include class testArrayCreateDestroy: public QRunnable { public: void run(void) { qlonglong N = 21; dtkDistributedArray *array = new dtkDistributedArray(N); QVERIFY(!array->empty()); QCOMPARE(array->size(), N); delete array; dtkDistributedMapper *mapper = new dtkDistributedMapper; array = new dtkDistributedArray(N, mapper); QVERIFY(!array->empty()); QCOMPARE(array->size(), N); QCOMPARE(array->mapper(), mapper); dtkDistributedArray *copy = new dtkDistributedArray(*array); QVERIFY(!copy->empty()); QVERIFY(!array->empty()); QCOMPARE(copy->size(), N); QCOMPARE(copy->mapper(), mapper); delete array; delete copy; array = new dtkDistributedArray(N, -1); QVERIFY(!array->empty()); QCOMPARE(array->size(), N); delete array; qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; array = new dtkDistributedArray(N, input); QVERIFY(!array->empty()); QCOMPARE(array->size(), N); delete array; delete[] input; } }; class testArrayAtFirstLast : public QRunnable { public: void run(void) { qlonglong N = 67; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; dtkDistributedArray array(N, input); for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { QCOMPARE(array.first(), input[0]); for (int j = 0; j < N; ++j) { QCOMPARE(array.at(j), input[j]); } QCOMPARE(array.last(), input[N - 1]); } comm->barrier(); } delete[] input; comm->barrier(); } }; class testArrayLocalInit : public QRunnable { public: void run(void) { qlonglong N = 67; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; qlonglong first = comm->rank() * N ; for (int i = 0; i < N; ++i) { input[i] = i + first; } dtkDistributedArray array(N * comm->size(), input, input + N); for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { QCOMPARE(array.first(), 0); for (int j = 0; j < N * comm->size(); ++j) { QCOMPARE(array.at(j), j ); } QCOMPARE(array.last(), N * comm->size() -1); } comm->barrier(); } delete[] input; comm->barrier(); } }; class testArrayFill : public QRunnable { public: void run(void) { qlonglong N = 67; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong input = 52687; dtkDistributedArray array(N, input); for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { for (int j = 0; j < N; ++j) { QCOMPARE(array.at(j), input); } } comm->barrier(); } comm->barrier(); } }; class testArrayPlusEqOperator : public QRunnable { public: void run(void) { qlonglong N = 67; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong input = 52687; dtkDistributedArray array(N, input); dtkDistributedArray array2(N, input); array += array2; for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { for (int j = 0; j < N; ++j) { QCOMPARE(array.at(j), 2 * input); } } comm->barrier(); } comm->barrier(); } }; class testArrayMult : public QRunnable { public: void run(void) { qlonglong N = 67; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong input = 52687; dtkDistributedArray array(N, input); array *= 45; for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { for (int j = 0; j < N; ++j) { QCOMPARE(array.at(j), 45 * input); } } comm->barrier(); } comm->barrier(); } }; class testArraySwap : public QRunnable { public: void run(void) { dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong N = 4; qlonglong input = -1; dtkDistributedArray array(N * comm->size(), input); comm->barrier(); qDebug() << "compare and swap" << N *comm->size(); qlonglong index = 0; for (int i = 0; i < N; ++i) { qlonglong value = comm->wid() + 42; while (!array.compareAndSwap(index, value, input) && index < N * comm->size()) { index ++; } QVERIFY(index < N * comm->size()); index ++; } comm->barrier(); if (comm->wid() == 0) { for (int i = 0; i < N * comm->size(); ++i) { qDebug() << i << array.at(i); QVERIFY(array.at(i) != input); } } } }; class testArrayOperatorGet : public QRunnable { public: void run(void) { qlonglong N = 107; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; dtkDistributedArray array(N, input); for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { for (int j = 0; j < N; ++j) { QCOMPARE(array[j], input[j]); } } comm->barrier(); } delete[] input; } }; class testArraySetAt : public QRunnable { public: void run(void) { qlonglong N = 107; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; dtkDistributedArray array(N); for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { for (int j = 0; j < N; ++j) { array.setAt(j, input[j]); } for (int j = 0; j < N; ++j) { QCOMPARE(array[j], input[j]); } } comm->barrier(); } array.fill(0); comm->barrier(); if (comm->wid() == 0) { array.setAt(0, input, N); } for (int i = 0; i < comm->size(); ++i) { if (comm->wid() == i) { for (int j = 0; j < N; ++j) { QCOMPARE(array[j], input[j]); } } comm->barrier(); } delete[] input; } }; class testArrayIterator : public QRunnable { public: void run(void) { qlonglong N = 16257; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; dtkDistributedArray array(N, input); dtkDistributedArray::iterator ite = array.begin(); dtkDistributedArray::iterator end = array.end(); for (int i = 0; ite != end; ++ite, ++i) { QCOMPARE(*ite, input[array.mapper()->localToGlobal(i, comm->wid())]); } dtkDistributedArray::const_iterator cite = array.cbegin(); dtkDistributedArray::const_iterator cend = array.cend(); for (int i = 0; cite != cend; ++cite, ++i) { QCOMPARE(*cite, input[array.mapper()->localToGlobal(i, comm->wid())]); } for (int i = 0; ite != end; ++ite, ++i) { *ite += i; QCOMPARE(*ite, input[array.mapper()->localToGlobal(i, comm->wid())] + i); } delete[] input; comm->barrier(); } }; class testArrayRemap : public QRunnable { public: void run(void) { qlonglong N = 200; qlonglong pu_size = dtkDistributed::app()->communicator()->size(); dtkDistributedArray array(N); qlonglong local_size = array.mapper()->count(dtkDistributed::app()->communicator()->wid()); dtkDistributedMapper *mapper = new dtkDistributedMapper; mapper->initMap(N, pu_size); qlonglong offset = 0; for (int i = 0; i < pu_size; ++i) { mapper->setMap(offset, i); offset += (local_size + i); } array.remap(mapper); qlonglong distance = std::distance(array.begin(), array.end()); local_size = array.mapper()->count(dtkDistributed::app()->communicator()->wid()); QCOMPARE(distance, local_size); } }; class testArrayCopyIntoArray : public QRunnable { public: void run(void) { qlonglong N = 107; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; dtkDistributedArray array(N, input); if (comm->wid() == 0) { for (int i = 0; i < comm->size(); ++i) { qlonglong size = array.mapper()->count(i); qlonglong fid = array.mapper()->firstIndex(i); qlonglong *output = new qlonglong[size]; qint32 owner = array.mapper()->owner(fid); array.copyIntoArray(fid, owner, output, size); for (int j = 0; j < size; ++j) { QCOMPARE(array[fid + j], output[j]); } delete[] output; } } comm->barrier(); delete[] input; } }; class testArrayToNavigator : public QRunnable { public: void run(void) { qlonglong N = 107; dtkDistributedCommunicator *comm = dtkDistributed::app()->communicator(); qlonglong *input = new qlonglong[N]; for (int i = 0; i < N; ++i) input[i] = i; dtkDistributedArray array(N, input); if (comm->wid() == 0) { dtkDistributedArray::navigator nav = array.toNavigator(); dtkDistributedArray::navigator::iterator ite = nav.begin(); dtkDistributedArray::navigator::iterator end = nav.end(); for (qlonglong i = 0; ite != end; ++i, ++ite) { QCOMPARE(*ite, input[i]); } } comm->barrier(); delete[] input; dtkDistributedArray::navigator nav = array.toNavigator(); nav.setRange(array.mapper()->firstIndex(comm->wid()), array.mapper()->count(comm->wid())); dtkDistributedArray::navigator::iterator nite = nav.begin(); dtkDistributedArray::navigator::iterator nend = nav.end(); dtkDistributedArray::iterator ite = array.begin(); for (; nite != nend; ++nite, ++ite) { QCOMPARE(*nite, *ite); } } }; namespace communicator_array_test { void inline runAll(QString type) { dtkDistributed::policy()->setType(type); while (dtkDistributed::policy()->hosts().size() < 4) dtkDistributed::policy()->addHost("localhost"); testArrayCreateDestroy work1; testArrayAtFirstLast work2; testArrayLocalInit work3; testArrayFill work4; testArrayPlusEqOperator work5; testArrayMult work6; testArraySwap work7; testArrayOperatorGet work8; testArraySetAt work9; testArrayIterator work10; testArrayRemap work11; testArrayCopyIntoArray work12; testArrayToNavigator work13; dtkDistributed::spawn(); dtkDistributed::exec(&work1); dtkDistributed::exec(&work2); dtkDistributed::exec(&work3); dtkDistributed::exec(&work4); dtkDistributed::exec(&work5); dtkDistributed::exec(&work6); dtkDistributed::exec(&work7); dtkDistributed::exec(&work8); dtkDistributed::exec(&work9); dtkDistributed::exec(&work10); dtkDistributed::exec(&work11); dtkDistributed::exec(&work12); dtkDistributed::exec(&work13); dtkDistributed::unspawn(); } } // // dtkDistributedArrayRunnable.h ends here