examples: add example program demonstrating sync entry methods
[charm.git] / examples / charm++ / matmul / matmul.ci
1 mainmodule matmul {
2   readonly CProxy_Main mainProxy;
3   mainchare Main {
4     entry Main(CkArgMsg *m);
5     entry [reductiontarget] void done();
6   };
7
8   array [2D] Block {
9     entry Block(unsigned int blockSize, unsigned int numBlocks);
10     entry void pdgemmSendInput(CProxy_Block output, bool aOrB) {
11       atomic {
12         if (aOrB)
13           output[thisIndex].inputA(0, data, blockSize, blockSize);
14         else
15           output[thisIndex].inputB(0, data, blockSize, blockSize);
16       }
17     };
18
19     entry void pdgemmRun(double alpha, double beta, CkCallback done) {
20       forall [block] (0:numBlocks-1,1) {
21         when
22           inputA[block](int blockIdA, double blockA[M*KA], unsigned int M, unsigned int KA),
23           inputB[block](int blockIdB, double blockB[KB*N], unsigned int KB, unsigned int N)
24           atomic {
25           CkAssert(KA == KB);
26
27           cblas_dgemm(CblasRowMajor, CblasNoTrans, CblasNoTrans,
28                       M, N, KA,
29                       alpha,
30                       blockA, KA, blockB, N,
31                       beta, data, N);
32
33           if (blockIdA != numBlocks) {
34             int destX = (thisIndex.x + 1) % numBlocks;
35             int destY = thisIndex.y;
36             thisProxy(destX, destY).inputA(blockIdA+1, blockA, M, KA);
37           }
38           if (blockIdB != numBlocks) {
39             int destX = thisIndex.x;
40             int destY = (thisIndex.y + 1) % numBlocks;
41             thisProxy(destX, destY).inputB(blockIdB+1, blockB, KB, N);
42           }
43         }
44       }
45       atomic {
46         contribute(done);
47       }
48     };
49     entry void inputA(int blockIdA, double blockA[M*KA], unsigned int M, unsigned int KA);
50     entry void inputB(int blockIdB, double blockB[KB*N], unsigned int KB, unsigned int N);
51   };
52 };