@@ -16,30 +16,71 @@ it, and the difference between the two is what each rung buys.
1616
1717```
1818mcpp.toml one dependency edge
19- build.mcpp scan the island , emit the boundary
19+ build.mcpp scan the root , emit the boundary
2020src/kernels/saxpy.c the island
21+ src/kernels/vec/scale.c a second island, one directory deeper
2122src/main.cpp import boundary.kernels;
2223```
2324
24- ` mcpp.tools.island ` reads the entry points marked ` MCPP_EXPORT_C ` and writes two
25- files into the build directory: the ` extern "C" ` header the island reads, and a
26- module over it whose whole content is a re-export.
25+ ` mcpp.tools.island ` reads the entry points marked ` MCPP_EXPORT_C ` under the root
26+ and writes two files into the build directory: the ` extern "C" ` header the
27+ island reads, and a module over it whose whole content is a re-export.
2728
2829``` cpp
2930// generated
3031module ;
3132#include " boundary.kernels.h"
3233export module boundary.kernels;
3334
34- export using ::saxpy_device;
35- export using ::saxpy_device_name;
35+ export namespace boundary ::kernels {
36+ using ::boundary_ran_on;
37+ inline constexpr auto ran_on = boundary_ran_on;
38+ using ::boundary_saxpy;
39+ inline constexpr auto saxpy = boundary_saxpy;
40+ }
41+
42+ export namespace boundary::kernels::vec {
43+ using ::boundary_scale;
44+ inline constexpr auto scale = boundary_scale;
45+ }
3646```
3747
3848Re-exporting names rather than restating signatures is what lets the generator
3949work without a C parser: it needs only the identifier before the `(`. It is also
4050why no second copy of a signature exists — at a C-linkage boundary that is the
4151copy that can disagree without anything noticing.
4252
53+ ## The namespace is the module's own path, and a directory extends it
54+
55+ This is the rule the shader lane already followed and this generator did not
56+ until `mcpp:plugins` 0.5.0.
57+ [`docs/42`](../../../docs/42-heterogeneous-builds.md) states it once for both
58+ lanes:
59+
60+ | written | reached as |
61+ |---|---|
62+ | `shaders/post/tonemap.frag` | `myapp::shaders::post::tonemap_frag()` |
63+ | `boundary_scale` in `src/kernels/vec/scale.c` | `boundary::kernels::vec::boundary_scale` |
64+
65+ The leaf differs and the reason is visible in the table. A payload has no name
66+ of its own, so the data lane derives one from the file name; an entry point
67+ already carries one its author wrote, so the file name reaches nothing here. A
68+ directory is the coarser unit either way, and moving a function between two
69+ files in one directory renames nothing a consumer wrote.
70+
71+ **`saxpy` beside `boundary_saxpy`.** An island's symbol is global to the whole
72+ program, so an entry point carries a package prefix whether or not it sits in a
73+ namespace, and the namespace then repeats it. `options::strip_prefix` emits the
74+ short spelling; the authored name is the symbol, is exported too, and is what
75+ `nm`, a link error and a profiler show. The pair is one symbol — the short name
76+ is a `constexpr` function pointer, not a second function.
77+
78+ **What the namespace does not buy.** C language linkage does not mangle, so two
79+ entry points with one name are one symbol whatever namespace each appears in.
80+ The generator therefore refuses two files in one root declaring one name, and
81+ that refusal is what makes the namespace honest: a name exists in exactly one of
82+ them.
83+
4384## The island is C here, and that is the only simplification
4485
4586An ordinary `.c` file, so this example runs on any machine with no device
@@ -54,7 +95,7 @@ and nothing about the boundary changes when that happens.
5495|---|---|---|---|
5596| **L0 — this example** | nothing but the marked entry points | `import boundary.kernels` | the island's own interface: pointers and a count |
5697| L1 — `../cuda`, `../sycl` | a seam module over the generated one | `import app.saxpy` | the interface the project designed |
57- | L2 | a seam, and the entry list passed to ` emit ` directly | ` import app.saxpy ` | the same, for entry points a scan cannot see |
98+ | L2 | a seam, and entries built with `island::declared` | `import app.saxpy` | the same, for entry points a scan cannot see |
5899| L3 — `../hip`, `../vulkan`, `../cann` | the header and the module | `import app.saxpy` | the same, with the signature written twice |
59100
60101**What L0 does not have.** The interface is C-shaped:
0 commit comments