/* * 697_samemod_prefer — same-module preference for bare-leaf lookup. * * Two modules each export `read` with intentionally distinct * signatures (mod1: i32 → i32, mod2: str → i32). Each module's * `caller()` invokes bare `read(...)` with its own arg type. The * bare-leaf lookup must resolve to the SAME-MODULE `read`; otherwise * the call is a check-time signature mismatch. * * Pre-fix (flat scope, first-wins by hash order): one of the bare * lookups picked the wrong module's `read` and the build failed with * "argument type not assignable". Post-fix (scope_lookup_prefer): each * bare-leaf inside its own module binds to the same-module entry, both * calls type-check, and the build succeeds. * * Runtime exit codes aren't asserted here because cgen still emits * unmangled `TEXT read` labels for both modules and the linker * collapses them. Mangling fn labels by module is a separate codegen * sweep; this test pins the resolver fix alone. * * Fixtures live in test/wcc/data/samemodprefer/. Same shape as * 696_modtype_leaf_collision.c. */ #include #include #include #include #include #include static int runwait(const char *cmd) { int rc = system(cmd); if (rc == -1) return -1; if (WIFEXITED(rc)) return WEXITSTATUS(rc); return -1; } static int run_pos(const char *driver, const char *fixdir, const char *tag) { char cmd[2048]; /* cd into the fixture dir so the driver's source-dir-first * import search resolves `use mod1; use mod2;`. */ snprintf(cmd, sizeof cmd, "cd %s && %s build pos.ww >/dev/null 2>&1", fixdir, driver); if (runwait(cmd) != 0) { fprintf(stderr, "samemod_prefer[%s]: pos.ww build failed — bare-leaf " "`read` lookup likely cross-bound\n", tag); return 1; } char bin[2048]; snprintf(bin, sizeof bin, "%s/pos", fixdir); unlink(bin); return 0; } int main(void) { const char *bin = getenv("BIN"); if (!bin) bin = "out/bin"; char absbin[1024]; if (bin[0] != '/') { char cwd[1024]; if (getcwd(cwd, sizeof cwd) == NULL) return 1; snprintf(absbin, sizeof absbin, "%s/%s", cwd, bin); bin = absbin; } char cdrv[1024]; snprintf(cdrv, sizeof cdrv, "%s/ww", bin); char fixdir[1024]; if (getcwd(fixdir, sizeof fixdir) == NULL) return 1; size_t cwd_n = strlen(fixdir); const char *rel = "/test/wcc/data/samemodprefer"; if (cwd_n + strlen(rel) + 1 >= sizeof fixdir) return 1; memcpy(fixdir + cwd_n, rel, strlen(rel) + 1); int fail = 0; fail += run_pos(cdrv, fixdir, "cstage"); if (fail) { fprintf(stderr, "samemod_prefer: %d case(s) failed\n", fail); return 1; } printf("samemod_prefer: 1/1 ok\n"); return 0; }