mirror of
https://github.com/DeusData/codebase-memory-mcp.git
synced 2026-11-04 18:58:00 +00:00
fix(resolver): Rust model cleanup: one-pass auto targets, in-scope own trait, IntoIterator items
Auto-discovered crate targets were matched per package, which was packages times files; they now take one pass after the package loop. A trait's own module always has it in scope. A project IntoIterator impl names its element in type Item, the same as Iterator. Separately, a field colliding with a method no longer marks the method as a signature twin, which had hidden about 120 genuine CALLS behind an unknown return type. Measured on meilisearch: CALLS 16,405 to 16,521, 3 lost, 119 gained. Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>
This commit is contained in:
1 parent
4860aa1b74
commit
1a0f97b8f3
3 files changed
+16
-17
No files matched your search
@@ -657,9 +657,8 @@ static rs_env_t rs_env_here(rs_walk_t *w) {
|
||||
|
||||
static bool rs_inst_binds_trait(rs_walk_t *w, rs_inst_t *inst, const rs_item_t *trait) {
|
||||
const rs_mod_t *syn = inst->syn;
|
||||
for (int i = 0; i < syn->nitems; i++)
|
||||
if (syn->items[i] == trait)
|
||||
return true;
|
||||
if (trait->owner == syn)
|
||||
return true;
|
||||
for (const rs_use_t *use = syn->uses; use; use = use->next) {
|
||||
if (!use->nseg || strcmp(use->segs[use->nseg - 1], trait->name) != 0)
|
||||
continue;
|
||||
@@ -2766,8 +2765,7 @@ static const rs_type_t *rs_element_of(rs_walk_t *w, const rs_type_t *iterable) {
|
||||
} else if (type->kind == RT_ITEM) {
|
||||
/* A project iterator names its element in `type Item = X`. */
|
||||
for (const rs_impl_t *impl = type->item->impls; impl; impl = impl->next_self) {
|
||||
if (!impl->trait_syn || impl->trait_syn->kind != RS_TS_PATH || !impl->trait_syn->nseg ||
|
||||
strcmp(impl->trait_syn->segs[impl->trait_syn->nseg - 1], "Iterator") != 0)
|
||||
if (!rs_iterator_trait_name(rs_tsyn_leaf(impl->trait_syn)))
|
||||
continue;
|
||||
for (int i = 0; i < impl->nassoc; i++) {
|
||||
if (strcmp(impl->assoc_names[i], "Item") != 0)
|
||||
|
||||
@@ -1561,10 +1561,15 @@ static void rs_package_crates(cbm_rust_project_t *project, rs_package_t *package
|
||||
rs_join(arena, package->dir, package->build_path ? package->build_path : "build.rs");
|
||||
if (build_rel)
|
||||
(void)rs_crate_add(project, package, "build_script_build", build_rel, RS_CRATE_AUX);
|
||||
}
|
||||
|
||||
/* src/bin, tests, benches and examples of whichever package owns each file. */
|
||||
static void rs_auto_crates(cbm_rust_project_t *project) {
|
||||
CBMArena *arena = &project->arena;
|
||||
for (int i = 0; i < project->nfiles; i++) {
|
||||
const char *rel = project->files[i]->rel, *rest = NULL;
|
||||
if (rs_owning_package(project, rel) != package || !rs_under(rel, package->dir, &rest) ||
|
||||
rs_target_listed(package, rel, arena))
|
||||
rs_package_t *package = (rs_package_t *)rs_owning_package(project, rel);
|
||||
if (!package || !package->name || !rs_under(rel, package->dir, &rest))
|
||||
continue;
|
||||
const char *name = NULL;
|
||||
rs_crate_kind_t kind = RS_CRATE_AUX;
|
||||
@@ -1574,7 +1579,8 @@ static void rs_package_crates(cbm_rust_project_t *project, rs_package_t *package
|
||||
!(package->auto_benches && (name = rs_auto_target(arena, rest, "benches/"))) &&
|
||||
!(package->auto_examples && (name = rs_auto_target(arena, rest, "examples/"))))
|
||||
continue;
|
||||
(void)rs_crate_add(project, package, rs_folded(arena, name), rel, kind);
|
||||
if (!rs_target_listed(package, rel, arena))
|
||||
(void)rs_crate_add(project, package, rs_folded(arena, name), rel, kind);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1686,6 +1692,7 @@ bool cbm_rust_project_seal(cbm_rust_project_t *project) {
|
||||
if (package->has_package && package->name)
|
||||
rs_package_crates(project, package);
|
||||
}
|
||||
rs_auto_crates(project);
|
||||
if (!any_manifest) {
|
||||
/* Without a manifest an entry file is an explicit rustc root. */
|
||||
for (int i = 0; i < project->nfiles; i++) {
|
||||
|
||||
@@ -503,15 +503,9 @@ TEST(javascript_import_table) {
|
||||
}
|
||||
|
||||
/* ═══════════════════════════════════════════════════════════════════════════
|
||||
* Rust — parse_rust_imports (text-based: strips "use "/";" from whole node).
|
||||
*
|
||||
* EXPECTED: basic and namespaced forms GREEN; grouped/braced forms may be RED
|
||||
* because the whole `use std::io::{self, Write};` text becomes the module_path,
|
||||
* so has_import("std::io") would still match as a substring — likely GREEN even
|
||||
* for grouped. The alias form `use X as Y;` leaves "std::collections::HashMap as H"
|
||||
* as module_path — has_import("std::collections::HashMap") would still match.
|
||||
* So most forms should be GREEN at extraction. Graph-level zero edges are
|
||||
* downstream.
|
||||
* Rust — parse_rust_imports: one import per use-tree leaf, each with its whole
|
||||
* path. `use std::io::{self, Write};` is "std::io" and "std::io::Write", and an
|
||||
* alias changes the local name, never the path.
|
||||
* ═══════════════════════════════════════════════════════════════════════════ */
|
||||
|
||||
static const import_case_t rust_cases[] = {
|
||||
|
||||
Reference in new issue
Block a user