--- title: malpp related: - "[cesga-ft3-skill](cesga-ft3-skill.md)" categories: - Languages and compilers --- **malpp** is a preprocessor abstraction layer for libmalleable: it lets you make an MPI program malleable (able to change its number of processes while it runs) by adding comments above its loops. ## Example With malpp, a malleable sum of squares only needs directives: ``` long i = 0, iters = 10, sum = 0; // mal: loop i->iters acc=sum for (; i < iters; i++) { sum += i * i; // mal: check } // mal: single printf("sum=%ld\n", sum); ``` Without it: ``` mal_init(); const long total = 10; long i, limit, sum = 0; MalFor f = mal_for(total, i, limit); mal_attach_acc(f, sum); for (; i < limit; i++) { sum += i * i; mal_check_for(f); } mal_finalize(); if (mal_rank() == 0) printf("sum=%ld\n", sum); ``` ## Building malpp is a flex and bison program: ``` $ make # builds ./malpp $ make test # also needs MPI; clones and builds libmalleable ``` ## Usage It reads a file (or stdin) and writes the expanded source to stdout: ``` $ malpp program.c > program_malleable.c ``` Or from a Makefile: ``` program_malleable.c: program.c malpp $^ > $@ ``` > [!TIP] > Build the generated code with `-O1` or higher: the dispatch scaffolding > malpp emits is correct unoptimized, but only folds away with optimization. ## Directives ### mal: loop `// mal: loop i->iters` declares a single linear loop. The variables are declared outside, the iterator starts at zero, and `// mal: check` must appear in the body. `acc=var` adds an accumulator for loops that count or sum. It must be a type libmalleable can reduce (`int`, `long`, `long long`, `unsigned`, `unsigned long`, `float`, `double`), and after the loop it is only meaningful on rank 0. ### mal: single `// mal: single` guards the statement below it so only rank 0 runs it. ### mal: decide `// mal: decide=` sets a custom resize decision function. Guard its definition with `#ifdef MALPP` so the sequential build still compiles. `// mal: decide=:` loads it at runtime from a shared library instead, with no guard needed. ## See also - [Source code](https://github.com/hugoocoto/malpp)