gitnexus 1.6.6-rc.12 → 1.6.6-rc.13
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/_shared/scope-resolution/reference-site.d.ts +8 -0
- package/dist/_shared/scope-resolution/reference-site.d.ts.map +1 -1
- package/dist/_shared/scope-resolution/registries/context.d.ts +8 -1
- package/dist/_shared/scope-resolution/registries/context.d.ts.map +1 -1
- package/dist/_shared/scope-resolution/registries/context.js.map +1 -1
- package/dist/core/ingestion/languages/cpp/captures.js +165 -9
- package/dist/core/ingestion/languages/cpp/constraint-filter.js +102 -32
- package/dist/core/ingestion/languages/cpp/type-classifier.d.ts +9 -9
- package/dist/core/ingestion/languages/cpp/type-classifier.js +12 -8
- package/dist/core/ingestion/scope-extractor.js +4 -0
- package/dist/core/ingestion/scope-resolution/passes/free-call-fallback.d.ts +1 -0
- package/dist/core/ingestion/scope-resolution/passes/free-call-fallback.js +4 -0
- package/dist/core/ingestion/scope-resolution/passes/overload-narrowing.d.ts +2 -0
- package/dist/core/ingestion/scope-resolution/passes/overload-narrowing.js +8 -1
- package/dist/core/ingestion/scope-resolution/passes/receiver-bound-calls.js +2 -0
- package/package.json +1 -1
|
@@ -20,6 +20,7 @@
|
|
|
20
20
|
* resolution step that reads this record and produces a `Reference`
|
|
21
21
|
* (defined in `./types.ts`).
|
|
22
22
|
*/
|
|
23
|
+
import type { ParameterTypeClass } from './symbol-definition.js';
|
|
23
24
|
import type { Range, ScopeId } from './types.js';
|
|
24
25
|
/**
|
|
25
26
|
* What kind of usage this reference represents — the graph-edge kind
|
|
@@ -71,5 +72,12 @@ export interface ReferenceSite {
|
|
|
71
72
|
* (C#: `42` → `'int'`, `"alice"` → `'string'`).
|
|
72
73
|
*/
|
|
73
74
|
readonly argumentTypes?: readonly string[];
|
|
75
|
+
/**
|
|
76
|
+
* Optional per-argument type-shape sidecar for languages that need
|
|
77
|
+
* cv/ref/pointer distinctions during constraint filtering. This is
|
|
78
|
+
* intentionally separate from `argumentTypes`, which stays normalized
|
|
79
|
+
* for existing overload narrowing and conversion-rank logic.
|
|
80
|
+
*/
|
|
81
|
+
readonly argumentTypeClasses?: readonly ParameterTypeClass[];
|
|
74
82
|
}
|
|
75
83
|
//# sourceMappingURL=reference-site.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reference-site.d.ts","sourceRoot":"","sources":["../../src/scope-resolution/reference-site.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEH,OAAO,KAAK,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AAEjD;;;;;;GAMG;AACH,MAAM,MAAM,aAAa,GACrB,MAAM,GACN,MAAM,GACN,OAAO,GACP,gBAAgB,GAChB,UAAU,GACV,YAAY,CAAC;AAEjB;;;;;;;;;GASG;AACH,MAAM,MAAM,QAAQ,GAAG,MAAM,GAAG,QAAQ,GAAG,aAAa,GAAG,OAAO,CAAC;AAEnE,MAAM,WAAW,aAAa;IAC5B,uEAAuE;IACvE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,2CAA2C;IAC3C,QAAQ,CAAC,OAAO,EAAE,KAAK,CAAC;IACxB;;;;OAIG;IACH,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAC1B,QAAQ,CAAC,IAAI,EAAE,aAAa,CAAC;IAC7B,kCAAkC;IAClC,QAAQ,CAAC,QAAQ,CAAC,EAAE,QAAQ,CAAC;IAC7B;;;OAGG;IACH,QAAQ,CAAC,gBAAgB,CAAC,EAAE;QAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC;IACtD,8EAA8E;IAC9E,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IACxB;;;;;;OAMG;IACH,QAAQ,CAAC,aAAa,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;
|
|
1
|
+
{"version":3,"file":"reference-site.d.ts","sourceRoot":"","sources":["../../src/scope-resolution/reference-site.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEH,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AACjE,OAAO,KAAK,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AAEjD;;;;;;GAMG;AACH,MAAM,MAAM,aAAa,GACrB,MAAM,GACN,MAAM,GACN,OAAO,GACP,gBAAgB,GAChB,UAAU,GACV,YAAY,CAAC;AAEjB;;;;;;;;;GASG;AACH,MAAM,MAAM,QAAQ,GAAG,MAAM,GAAG,QAAQ,GAAG,aAAa,GAAG,OAAO,CAAC;AAEnE,MAAM,WAAW,aAAa;IAC5B,uEAAuE;IACvE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,2CAA2C;IAC3C,QAAQ,CAAC,OAAO,EAAE,KAAK,CAAC;IACxB;;;;OAIG;IACH,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAC1B,QAAQ,CAAC,IAAI,EAAE,aAAa,CAAC;IAC7B,kCAAkC;IAClC,QAAQ,CAAC,QAAQ,CAAC,EAAE,QAAQ,CAAC;IAC7B;;;OAGG;IACH,QAAQ,CAAC,gBAAgB,CAAC,EAAE;QAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC;IACtD,8EAA8E;IAC9E,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IACxB;;;;;;OAMG;IACH,QAAQ,CAAC,aAAa,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAC3C;;;;;OAKG;IACH,QAAQ,CAAC,mBAAmB,CAAC,EAAE,SAAS,kBAAkB,EAAE,CAAC;CAC9D"}
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
* reaches into the CLI package.
|
|
13
13
|
*/
|
|
14
14
|
import type { NodeLabel } from '../../graph/types.js';
|
|
15
|
-
import type { SymbolDefinition } from '../symbol-definition.js';
|
|
15
|
+
import type { ParameterTypeClass, SymbolDefinition } from '../symbol-definition.js';
|
|
16
16
|
import type { Callsite, DefId } from '../types.js';
|
|
17
17
|
import type { DefIndex } from '../def-index.js';
|
|
18
18
|
import type { QualifiedNameIndex } from '../qualified-name-index.js';
|
|
@@ -54,6 +54,13 @@ export interface ConstraintContext {
|
|
|
54
54
|
* `narrowOverloadCandidates`' `argTypes` parameter.
|
|
55
55
|
*/
|
|
56
56
|
readonly argumentTypes?: readonly string[];
|
|
57
|
+
/**
|
|
58
|
+
* Optional shape-preserving sidecar aligned with `argumentTypes`.
|
|
59
|
+
* Unknown or unsupported slots should be omitted by producers or
|
|
60
|
+
* marked with `indirection: 'unknown'`; consumers must preserve the
|
|
61
|
+
* monotonic fallback and return 'unknown' instead of guessing.
|
|
62
|
+
*/
|
|
63
|
+
readonly argumentTypeClasses?: readonly ParameterTypeClass[];
|
|
57
64
|
}
|
|
58
65
|
/**
|
|
59
66
|
* Per-owner membership view plugged into `LookupParams.ownerScopedContributor`.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../../src/scope-resolution/registries/context.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AACtD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;
|
|
1
|
+
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../../../src/scope-resolution/registries/context.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AACtD,OAAO,KAAK,EAAE,kBAAkB,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AACpF,OAAO,KAAK,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,aAAa,CAAC;AACnD,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAChD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,4BAA4B,CAAC;AACrE,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AACjE,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,kBAAkB,CAAC;AAClD,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,6BAA6B,CAAC;AAIvE,MAAM,WAAW,iBAAiB;IAChC;;;;OAIG;IACH,kBAAkB,CAAC,CAAC,QAAQ,EAAE,QAAQ,EAAE,GAAG,EAAE,gBAAgB,GAAG,YAAY,CAAC;IAE7E;;;;;;;;;;OAUG;IACH,uBAAuB,CAAC,CACtB,QAAQ,EAAE,QAAQ,EAClB,GAAG,EAAE,gBAAgB,EACrB,GAAG,EAAE,iBAAiB,GACrB,YAAY,CAAC;CACjB;AAED,MAAM,MAAM,YAAY,GAAG,YAAY,GAAG,SAAS,GAAG,cAAc,CAAC;AAErE;;;;;;GAMG;AACH,MAAM,WAAW,iBAAiB;IAChC;;;;OAIG;IACH,QAAQ,CAAC,aAAa,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAC3C;;;;;OAKG;IACH,QAAQ,CAAC,mBAAmB,CAAC,EAAE,SAAS,kBAAkB,EAAE,CAAC;CAC9D;AAID;;;;;;;;;;;;GAYG;AACH,MAAM,WAAW,sBAAsB;IACrC,sEAAsE;IACtE,QAAQ,CAAC,UAAU,EAAE,KAAK,CAAC;IAC3B;;;;OAIG;IACH,MAAM,CAAC,IAAI,EAAE,MAAM,GAAG,SAAS,gBAAgB,EAAE,CAAC;CACnD;AAED;;;;;;;GAOG;AACH,MAAM,MAAM,yBAAyB,GAAG,CACtC,UAAU,EAAE,KAAK,EACjB,UAAU,EAAE,MAAM,KACf,SAAS,gBAAgB,EAAE,CAAC;AAIjC,MAAM,WAAW,eAAe;IAC9B,QAAQ,CAAC,MAAM,EAAE,SAAS,CAAC;IAC3B,QAAQ,CAAC,IAAI,EAAE,QAAQ,CAAC;IACxB,QAAQ,CAAC,cAAc,EAAE,kBAAkB,CAAC;IAC5C,QAAQ,CAAC,YAAY,EAAE,gBAAgB,CAAC;IACxC,QAAQ,CAAC,mBAAmB,EAAE,yBAAyB,CAAC;IACxD;;;OAGG;IACH,QAAQ,CAAC,cAAc,CAAC,EAAE,mBAAmB,CAAC;IAC9C,QAAQ,CAAC,SAAS,EAAE,iBAAiB,CAAC;CACvC;AAOD,eAAO,MAAM,WAAW,EAAE,SAAS,SAAS,EAc1C,CAAC;AAEH,eAAO,MAAM,YAAY,EAAE,SAAS,SAAS,EAI3C,CAAC;AAEH,eAAO,MAAM,WAAW,EAAE,SAAS,SAAS,EAK1C,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"context.js","sourceRoot":"","sources":["../../../src/scope-resolution/registries/context.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;
|
|
1
|
+
{"version":3,"file":"context.js","sourceRoot":"","sources":["../../../src/scope-resolution/registries/context.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAuHH,8EAA8E;AAC9E,EAAE;AACF,0EAA0E;AAC1E,6DAA6D;AAE7D,MAAM,CAAC,MAAM,WAAW,GAAyB,MAAM,CAAC,MAAM,CAAC;IAC7D,OAAO;IACP,WAAW;IACX,MAAM;IACN,QAAQ;IACR,OAAO;IACP,OAAO;IACP,WAAW;IACX,SAAS;IACT,QAAQ;IACR,UAAU;IACV,YAAY;IACZ,UAAU;IACV,WAAW;CACZ,CAAC,CAAC;AAEH,MAAM,CAAC,MAAM,YAAY,GAAyB,MAAM,CAAC,MAAM,CAAC;IAC9D,QAAQ;IACR,UAAU;IACV,aAAa;CACd,CAAC,CAAC;AAEH,MAAM,CAAC,MAAM,WAAW,GAAyB,MAAM,CAAC,MAAM,CAAC;IAC7D,UAAU;IACV,UAAU;IACV,OAAO;IACP,QAAQ;CACT,CAAC,CAAC"}
|
|
@@ -3,7 +3,7 @@ import { getCppParser, getCppScopeQuery } from './query.js';
|
|
|
3
3
|
import { getTreeSitterBufferSize } from '../../constants.js';
|
|
4
4
|
import { parseSourceSafe } from '../../../tree-sitter/safe-parse.js';
|
|
5
5
|
import { splitCppInclude, splitCppUsingDecl } from './import-decomposer.js';
|
|
6
|
-
import { computeCppDeclarationArity, computeCppCallArity } from './arity-metadata.js';
|
|
6
|
+
import { classifyCppParameterType, computeCppDeclarationArity, computeCppCallArity, } from './arity-metadata.js';
|
|
7
7
|
import { markCppAnonymousNamespaceRange, markFileLocal } from './file-local-linkage.js';
|
|
8
8
|
import { markCppDependentBase } from './two-phase-lookup.js';
|
|
9
9
|
import { markCppAdlSiteArgs, markCppAdlSiteNoAdl } from './adl.js';
|
|
@@ -159,6 +159,10 @@ export function emitCppScopeCaptures(sourceText, filePath, cachedTree) {
|
|
|
159
159
|
if (argTypes !== undefined && argTypes.length > 0) {
|
|
160
160
|
grouped['@reference.parameter-types'] = syntheticCapture('@reference.parameter-types', cNode, JSON.stringify(argTypes));
|
|
161
161
|
}
|
|
162
|
+
const argTypeClasses = inferCppCallArgTypeClasses(cNode);
|
|
163
|
+
if (argTypeClasses !== undefined && argTypeClasses.length > 0) {
|
|
164
|
+
grouped['@reference.parameter-type-classes'] = syntheticCapture('@reference.parameter-type-classes', cNode, JSON.stringify(argTypeClasses));
|
|
165
|
+
}
|
|
162
166
|
}
|
|
163
167
|
}
|
|
164
168
|
// ── Inline namespace detection ──────────────────────────────────
|
|
@@ -612,6 +616,36 @@ function inferCppCallArgTypes(node) {
|
|
|
612
616
|
}
|
|
613
617
|
return types.length > 0 ? types : undefined;
|
|
614
618
|
}
|
|
619
|
+
function inferCppCallArgTypeClasses(node) {
|
|
620
|
+
const argList = node.childForFieldName('arguments');
|
|
621
|
+
if (argList === null)
|
|
622
|
+
return undefined;
|
|
623
|
+
const classes = [];
|
|
624
|
+
for (let i = 0; i < argList.childCount; i++) {
|
|
625
|
+
const child = argList.child(i);
|
|
626
|
+
if (child === null)
|
|
627
|
+
continue;
|
|
628
|
+
if (child.type === ',' || child.type === '(' || child.type === ')')
|
|
629
|
+
continue;
|
|
630
|
+
const litType = inferCppLiteralType(child);
|
|
631
|
+
if (litType !== '') {
|
|
632
|
+
classes.push(valueTypeClass(litType));
|
|
633
|
+
}
|
|
634
|
+
else if (child.type === 'identifier') {
|
|
635
|
+
classes.push(lookupDeclaredTypeClassForIdentifier(child));
|
|
636
|
+
}
|
|
637
|
+
else {
|
|
638
|
+
classes.push(unknownTypeClass('unknown'));
|
|
639
|
+
}
|
|
640
|
+
}
|
|
641
|
+
return classes.length > 0 ? classes : undefined;
|
|
642
|
+
}
|
|
643
|
+
function valueTypeClass(base) {
|
|
644
|
+
return { base, cv: 'none', indirection: 'value', pointerDepth: 0 };
|
|
645
|
+
}
|
|
646
|
+
function unknownTypeClass(base) {
|
|
647
|
+
return { base, cv: 'unknown', indirection: 'unknown', pointerDepth: 0 };
|
|
648
|
+
}
|
|
615
649
|
/**
|
|
616
650
|
* Infer the canonical type name of a C++ literal AST node.
|
|
617
651
|
* Returns empty string for non-literal / unknown nodes.
|
|
@@ -674,6 +708,9 @@ function lookupDeclaredTypeForIdentifier(identNode) {
|
|
|
674
708
|
}
|
|
675
709
|
if (scope === null)
|
|
676
710
|
return '';
|
|
711
|
+
const paramType = lookupFunctionParameterType(scope, varName);
|
|
712
|
+
if (paramType !== '')
|
|
713
|
+
return paramType;
|
|
677
714
|
// Scan declarations in the scope for a matching variable name
|
|
678
715
|
for (let i = 0; i < scope.childCount; i++) {
|
|
679
716
|
const stmt = scope.child(i);
|
|
@@ -689,18 +726,113 @@ function lookupDeclaredTypeForIdentifier(identNode) {
|
|
|
689
726
|
const declarator = stmt.childForFieldName('declarator');
|
|
690
727
|
if (declarator === null)
|
|
691
728
|
continue;
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
if (nameChild !== null && nameChild.text === varName) {
|
|
695
|
-
return normalizeCppTypeText(typeNode.text);
|
|
696
|
-
}
|
|
697
|
-
}
|
|
698
|
-
else if (declarator.text === varName) {
|
|
729
|
+
const nameChild = declaredNameNode(declarator);
|
|
730
|
+
if (nameChild !== null && extractDeclaratorLeafName(nameChild) === varName) {
|
|
699
731
|
return normalizeCppTypeText(typeNode.text);
|
|
700
732
|
}
|
|
701
733
|
}
|
|
702
734
|
return '';
|
|
703
735
|
}
|
|
736
|
+
function lookupDeclaredTypeClassForIdentifier(identNode) {
|
|
737
|
+
const varName = identNode.text;
|
|
738
|
+
let scope = identNode.parent;
|
|
739
|
+
while (scope !== null &&
|
|
740
|
+
scope.type !== 'compound_statement' &&
|
|
741
|
+
scope.type !== 'translation_unit') {
|
|
742
|
+
scope = scope.parent;
|
|
743
|
+
}
|
|
744
|
+
if (scope === null)
|
|
745
|
+
return unknownTypeClass('unknown');
|
|
746
|
+
const paramTypeClass = lookupFunctionParameterTypeClass(scope, varName, identNode);
|
|
747
|
+
if (paramTypeClass !== undefined)
|
|
748
|
+
return paramTypeClass;
|
|
749
|
+
for (let i = 0; i < scope.childCount; i++) {
|
|
750
|
+
const stmt = scope.child(i);
|
|
751
|
+
if (stmt === null || stmt.type !== 'declaration')
|
|
752
|
+
continue;
|
|
753
|
+
const typeNode = stmt.childForFieldName('type');
|
|
754
|
+
if (typeNode === null)
|
|
755
|
+
continue;
|
|
756
|
+
if (typeNode.type === 'placeholder_type_specifier')
|
|
757
|
+
continue;
|
|
758
|
+
const declarator = stmt.childForFieldName('declarator');
|
|
759
|
+
if (declarator === null)
|
|
760
|
+
continue;
|
|
761
|
+
const nameChild = declaredNameNode(declarator);
|
|
762
|
+
if (nameChild === null || extractDeclaratorLeafName(nameChild) !== varName)
|
|
763
|
+
continue;
|
|
764
|
+
const typeClass = classifyCppParameterType(typeNode.text, nameChild.text, stmt.text.replace(/;\s*$/, ''));
|
|
765
|
+
if (isKnownEnumName(identNode, typeClass.base)) {
|
|
766
|
+
return { ...typeClass, base: `enum:${typeClass.base}` };
|
|
767
|
+
}
|
|
768
|
+
return typeClass;
|
|
769
|
+
}
|
|
770
|
+
return unknownTypeClass('unknown');
|
|
771
|
+
}
|
|
772
|
+
function lookupFunctionParameterType(scope, varName) {
|
|
773
|
+
const param = findEnclosingFunctionParameter(scope, varName);
|
|
774
|
+
if (param === null)
|
|
775
|
+
return '';
|
|
776
|
+
const typeNode = param.childForFieldName('type');
|
|
777
|
+
if (typeNode === null)
|
|
778
|
+
return '';
|
|
779
|
+
return normalizeCppTypeText(typeNode.text);
|
|
780
|
+
}
|
|
781
|
+
function lookupFunctionParameterTypeClass(scope, varName, identNode) {
|
|
782
|
+
const param = findEnclosingFunctionParameter(scope, varName);
|
|
783
|
+
if (param === null)
|
|
784
|
+
return undefined;
|
|
785
|
+
const typeNode = param.childForFieldName('type');
|
|
786
|
+
if (typeNode === null)
|
|
787
|
+
return undefined;
|
|
788
|
+
const declarator = param.childForFieldName('declarator');
|
|
789
|
+
if (declarator === null)
|
|
790
|
+
return undefined;
|
|
791
|
+
const typeClass = classifyCppParameterType(typeNode.text, declarator.text, param.text);
|
|
792
|
+
if (isKnownEnumName(identNode, typeClass.base)) {
|
|
793
|
+
return { ...typeClass, base: `enum:${typeClass.base}` };
|
|
794
|
+
}
|
|
795
|
+
return typeClass;
|
|
796
|
+
}
|
|
797
|
+
function findEnclosingFunctionParameter(scope, varName) {
|
|
798
|
+
let node = scope.parent;
|
|
799
|
+
while (node !== null) {
|
|
800
|
+
if (node.type === 'function_definition' || node.type === 'function_declarator') {
|
|
801
|
+
const fnDecl = node.type === 'function_declarator'
|
|
802
|
+
? node
|
|
803
|
+
: findFirstDescendantOfType(node, 'function_declarator');
|
|
804
|
+
const params = fnDecl?.childForFieldName('parameters') ?? null;
|
|
805
|
+
if (params !== null) {
|
|
806
|
+
for (let i = 0; i < params.namedChildCount; i++) {
|
|
807
|
+
const param = params.namedChild(i);
|
|
808
|
+
if (param === null || param.type !== 'parameter_declaration')
|
|
809
|
+
continue;
|
|
810
|
+
const declarator = param.childForFieldName('declarator');
|
|
811
|
+
if (declarator !== null && extractDeclaratorLeafName(declarator) === varName) {
|
|
812
|
+
return param;
|
|
813
|
+
}
|
|
814
|
+
}
|
|
815
|
+
}
|
|
816
|
+
return null;
|
|
817
|
+
}
|
|
818
|
+
node = node.parent;
|
|
819
|
+
}
|
|
820
|
+
return null;
|
|
821
|
+
}
|
|
822
|
+
function declaredNameNode(declarator) {
|
|
823
|
+
if (declarator.type !== 'init_declarator')
|
|
824
|
+
return declarator;
|
|
825
|
+
for (let i = 0; i < declarator.namedChildCount; i++) {
|
|
826
|
+
const child = declarator.namedChild(i);
|
|
827
|
+
if (child === null)
|
|
828
|
+
continue;
|
|
829
|
+
if (child.type === 'identifier')
|
|
830
|
+
return child;
|
|
831
|
+
if (child.type.endsWith('_declarator'))
|
|
832
|
+
return child;
|
|
833
|
+
}
|
|
834
|
+
return declarator.childForFieldName('declarator');
|
|
835
|
+
}
|
|
704
836
|
/** Normalize a type-specifier text for argument type matching.
|
|
705
837
|
* Strips qualifiers (const, volatile), namespace prefixes (std::),
|
|
706
838
|
* and pointer/reference markers. */
|
|
@@ -711,6 +843,28 @@ function normalizeCppTypeText(text) {
|
|
|
711
843
|
t = t.replace(/[*&]/g, '').trim();
|
|
712
844
|
return t;
|
|
713
845
|
}
|
|
846
|
+
function isKnownEnumName(node, typeName) {
|
|
847
|
+
if (typeName === '' || typeName === 'unknown')
|
|
848
|
+
return false;
|
|
849
|
+
let root = node;
|
|
850
|
+
while (root.parent !== null)
|
|
851
|
+
root = root.parent;
|
|
852
|
+
const stack = [root];
|
|
853
|
+
while (stack.length > 0) {
|
|
854
|
+
const cur = stack.pop();
|
|
855
|
+
if (cur.type === 'enum_specifier') {
|
|
856
|
+
const name = cur.childForFieldName('name');
|
|
857
|
+
if (name?.text === typeName)
|
|
858
|
+
return true;
|
|
859
|
+
}
|
|
860
|
+
for (let i = 0; i < cur.childCount; i++) {
|
|
861
|
+
const child = cur.child(i);
|
|
862
|
+
if (child !== null)
|
|
863
|
+
stack.push(child);
|
|
864
|
+
}
|
|
865
|
+
}
|
|
866
|
+
return false;
|
|
867
|
+
}
|
|
714
868
|
/**
|
|
715
869
|
* Detect whether a `namespace_definition` AST node is inline.
|
|
716
870
|
* Tree-sitter-cpp exposes the `inline` keyword as an anonymous child
|
|
@@ -1166,7 +1320,9 @@ function extractDeclaratorLeafName(node) {
|
|
|
1166
1320
|
// Common wrapper nodes — follow the 'declarator' field when present.
|
|
1167
1321
|
const next = cur.childForFieldName('declarator') ??
|
|
1168
1322
|
// parenthesized_declarator: single named child
|
|
1169
|
-
(cur.type === 'parenthesized_declarator'
|
|
1323
|
+
(cur.type === 'parenthesized_declarator' || cur.type.endsWith('_declarator')
|
|
1324
|
+
? cur.namedChild(0)
|
|
1325
|
+
: null);
|
|
1170
1326
|
if (next === null)
|
|
1171
1327
|
return null;
|
|
1172
1328
|
cur = next;
|
|
@@ -21,13 +21,9 @@
|
|
|
21
21
|
*/
|
|
22
22
|
import { classifyType } from './type-classifier.js';
|
|
23
23
|
/**
|
|
24
|
-
* Curated Tier-A predicate registry
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
*
|
|
28
|
-
* Deferred predicates that need a cv/ref/pointer sidecar on
|
|
29
|
-
* `normalizeCppParamType` (today the normalizer strips those markers
|
|
30
|
-
* before storage) live in #1579 as one-line follow-up adds.
|
|
24
|
+
* Curated Tier-A predicate registry. Predicates that depend on pointer,
|
|
25
|
+
* reference, or cv shape consult `ConstraintContext.argumentTypeClasses`.
|
|
26
|
+
* Missing or unsupported shape returns 'unknown' to preserve monotonicity.
|
|
31
27
|
*/
|
|
32
28
|
// ISO `<type_traits>` treats `bool`, `char`, and the signed/unsigned char
|
|
33
29
|
// variants as integral types (§21.3.4 Table 48), so `is_integral_v<bool>`
|
|
@@ -39,40 +35,117 @@ function isIntegralClass(c) {
|
|
|
39
35
|
return c === 'integral' || c === 'bool' || c === 'char';
|
|
40
36
|
}
|
|
41
37
|
const REGISTRY = new Map([
|
|
42
|
-
[
|
|
43
|
-
|
|
38
|
+
[
|
|
39
|
+
'is_void_v',
|
|
40
|
+
(args) => unaryVerdict(args, (arg) => isPlainValue(arg) && arg.typeClass === 'void'),
|
|
41
|
+
],
|
|
42
|
+
[
|
|
43
|
+
'is_integral_v',
|
|
44
|
+
(args) => unaryVerdict(args, (arg) => isPlainValue(arg) && isIntegralClass(arg.typeClass)),
|
|
45
|
+
],
|
|
46
|
+
[
|
|
47
|
+
'is_floating_point_v',
|
|
48
|
+
(args) => unaryVerdict(args, (arg) => isPlainValue(arg) && arg.typeClass === 'floating'),
|
|
49
|
+
],
|
|
44
50
|
[
|
|
45
51
|
'is_arithmetic_v',
|
|
46
|
-
(
|
|
52
|
+
(args) => unaryVerdict(args, (arg) => isPlainValue(arg) && (isIntegralClass(arg.typeClass) || arg.typeClass === 'floating')),
|
|
53
|
+
],
|
|
54
|
+
[
|
|
55
|
+
'is_enum_v',
|
|
56
|
+
(args) => unaryVerdict(args, (arg) => isPlainValue(arg) && arg.typeClass === 'enum'),
|
|
57
|
+
],
|
|
58
|
+
[
|
|
59
|
+
'is_class_v',
|
|
60
|
+
(args) => unaryVerdict(args, (arg) => isPlainValue(arg) && arg.typeClass === 'class'),
|
|
61
|
+
],
|
|
62
|
+
[
|
|
63
|
+
'is_pointer_v',
|
|
64
|
+
(args) => unaryShapeVerdict(args, (shape) => shape.indirection === 'pointer' && shape.pointerDepth > 0),
|
|
65
|
+
],
|
|
66
|
+
[
|
|
67
|
+
'is_reference_v',
|
|
68
|
+
(args) => unaryShapeVerdict(args, (shape) => shape.indirection === 'lvalue-ref' || shape.indirection === 'rvalue-ref'),
|
|
69
|
+
],
|
|
70
|
+
[
|
|
71
|
+
'is_const_v',
|
|
72
|
+
(args) => unaryShapeVerdict(args, (shape) => shape.cv === 'const' || shape.cv === 'const volatile', {
|
|
73
|
+
requireTopLevelCv: true,
|
|
74
|
+
}),
|
|
75
|
+
],
|
|
76
|
+
[
|
|
77
|
+
'is_volatile_v',
|
|
78
|
+
(args) => unaryShapeVerdict(args, (shape) => shape.cv === 'volatile' || shape.cv === 'const volatile', {
|
|
79
|
+
requireTopLevelCv: true,
|
|
80
|
+
}),
|
|
47
81
|
],
|
|
48
|
-
// NOTE: cv-qualifiers are stripped by `normalizeCppParamType` before the
|
|
49
|
-
// type token reaches `classifyType`, so `is_same_v<const T, T>` returns
|
|
50
|
-
// `'compatible'` instead of the ISO-correct `false`. Tracked under the
|
|
51
|
-
// cv-sidecar refactor in #1579's "Out of scope" list; until that lands
|
|
52
|
-
// this approximation matches the common `is_same_v<T, ConcreteType>`
|
|
53
|
-
// dispatch idiom and silently degrades on cv-distinct compares.
|
|
54
82
|
[
|
|
55
83
|
'is_same_v',
|
|
56
|
-
(
|
|
57
|
-
if (
|
|
84
|
+
(args) => {
|
|
85
|
+
if (args.length < 2 || args[0].typeClass === 'unknown' || args[1].typeClass === 'unknown') {
|
|
58
86
|
return 'unknown';
|
|
59
|
-
|
|
87
|
+
}
|
|
88
|
+
return args[0].typeClass === args[1].typeClass ? 'compatible' : 'incompatible';
|
|
60
89
|
},
|
|
61
90
|
],
|
|
62
91
|
]);
|
|
63
|
-
function
|
|
64
|
-
|
|
92
|
+
function unaryVerdict(args, predicate) {
|
|
93
|
+
const arg = args[0];
|
|
94
|
+
if (arg === undefined || arg.typeClass === 'unknown')
|
|
65
95
|
return 'unknown';
|
|
66
|
-
return predicate ? 'compatible' : 'incompatible';
|
|
96
|
+
return predicate(arg) ? 'compatible' : 'incompatible';
|
|
97
|
+
}
|
|
98
|
+
function unaryShapeVerdict(args, predicate, options = {}) {
|
|
99
|
+
const arg = args[0];
|
|
100
|
+
if (arg === undefined || arg.typeClass === 'unknown')
|
|
101
|
+
return 'unknown';
|
|
102
|
+
const shape = arg.shape;
|
|
103
|
+
if (shape === undefined || shape.indirection === 'unknown' || shape.cv === 'unknown') {
|
|
104
|
+
return 'unknown';
|
|
105
|
+
}
|
|
106
|
+
if (options.requireTopLevelCv === true && shape.indirection === 'pointer') {
|
|
107
|
+
return 'unknown';
|
|
108
|
+
}
|
|
109
|
+
return predicate(shape) ? 'compatible' : 'incompatible';
|
|
110
|
+
}
|
|
111
|
+
function isPlainValue(arg) {
|
|
112
|
+
const shape = arg.shape;
|
|
113
|
+
if (shape === undefined)
|
|
114
|
+
return true;
|
|
115
|
+
return shape.indirection === 'value';
|
|
116
|
+
}
|
|
117
|
+
function classifyConstraintArg(token, shape) {
|
|
118
|
+
if (shape !== undefined && shape.base.startsWith('enum:')) {
|
|
119
|
+
return { typeClass: 'enum', shape };
|
|
120
|
+
}
|
|
121
|
+
const typeClass = token === undefined || token === '' ? 'unknown' : classifyType(token);
|
|
122
|
+
return { typeClass, ...(shape !== undefined ? { shape } : {}) };
|
|
123
|
+
}
|
|
124
|
+
function tokenForArg(ctx, argIdx) {
|
|
125
|
+
const shape = ctx.argumentTypeClasses?.[argIdx];
|
|
126
|
+
if (shape?.base.startsWith('enum:'))
|
|
127
|
+
return shape.base;
|
|
128
|
+
return ctx.argumentTypes?.[argIdx];
|
|
129
|
+
}
|
|
130
|
+
function shapeForTemplateParam(ctx, paramName, argIdx, def) {
|
|
131
|
+
const argShape = ctx.argumentTypeClasses?.[argIdx];
|
|
132
|
+
if (argShape === undefined)
|
|
133
|
+
return undefined;
|
|
134
|
+
const paramShape = def?.parameterTypeClasses?.[argIdx];
|
|
135
|
+
if (paramShape === undefined)
|
|
136
|
+
return argShape;
|
|
137
|
+
if (paramShape.base === paramName && paramShape.indirection === 'value')
|
|
138
|
+
return argShape;
|
|
139
|
+
return undefined;
|
|
67
140
|
}
|
|
68
141
|
/** Public surface — registered as `ScopeResolver.constraintCompatibility`. */
|
|
69
142
|
export function cppConstraintCompatibility(_callsite, def, ctx) {
|
|
70
143
|
const payload = def.templateConstraints;
|
|
71
144
|
if (payload === undefined)
|
|
72
145
|
return 'unknown';
|
|
73
|
-
return evaluate(payload.expr, payload, ctx);
|
|
146
|
+
return evaluate(payload.expr, payload, ctx, def);
|
|
74
147
|
}
|
|
75
|
-
function evaluate(expr, payload, ctx) {
|
|
148
|
+
function evaluate(expr, payload, ctx, def) {
|
|
76
149
|
switch (expr.kind) {
|
|
77
150
|
case 'unknown':
|
|
78
151
|
return 'unknown';
|
|
@@ -83,18 +156,15 @@ function evaluate(expr, payload, ctx) {
|
|
|
83
156
|
const classes = expr.args.map((paramName) => {
|
|
84
157
|
const argIdx = payload.paramArgIndex[paramName];
|
|
85
158
|
if (argIdx === undefined)
|
|
86
|
-
return 'unknown';
|
|
87
|
-
|
|
88
|
-
if (token === undefined || token === '')
|
|
89
|
-
return 'unknown';
|
|
90
|
-
return classifyType(token);
|
|
159
|
+
return { typeClass: 'unknown' };
|
|
160
|
+
return classifyConstraintArg(tokenForArg(ctx, argIdx), shapeForTemplateParam(ctx, paramName, argIdx, def));
|
|
91
161
|
});
|
|
92
162
|
return evaluator(classes);
|
|
93
163
|
}
|
|
94
164
|
case 'and': {
|
|
95
165
|
let result = 'compatible';
|
|
96
166
|
for (const child of expr.children) {
|
|
97
|
-
const v = evaluate(child, payload, ctx);
|
|
167
|
+
const v = evaluate(child, payload, ctx, def);
|
|
98
168
|
if (v === 'incompatible')
|
|
99
169
|
return 'incompatible';
|
|
100
170
|
if (v === 'unknown')
|
|
@@ -105,7 +175,7 @@ function evaluate(expr, payload, ctx) {
|
|
|
105
175
|
case 'or': {
|
|
106
176
|
let result = 'incompatible';
|
|
107
177
|
for (const child of expr.children) {
|
|
108
|
-
const v = evaluate(child, payload, ctx);
|
|
178
|
+
const v = evaluate(child, payload, ctx, def);
|
|
109
179
|
if (v === 'compatible')
|
|
110
180
|
return 'compatible';
|
|
111
181
|
if (v === 'unknown')
|
|
@@ -114,7 +184,7 @@ function evaluate(expr, payload, ctx) {
|
|
|
114
184
|
return result;
|
|
115
185
|
}
|
|
116
186
|
case 'not': {
|
|
117
|
-
const v = evaluate(expr.child, payload, ctx);
|
|
187
|
+
const v = evaluate(expr.child, payload, ctx, def);
|
|
118
188
|
if (v === 'compatible')
|
|
119
189
|
return 'incompatible';
|
|
120
190
|
if (v === 'incompatible')
|
|
@@ -7,20 +7,20 @@
|
|
|
7
7
|
* the call-site inference in `captures.ts`) to one of the categories
|
|
8
8
|
* the `<type_traits>` predicate registry uses for SFINAE filtering.
|
|
9
9
|
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
*
|
|
14
|
-
* ("including any cv-qualified variants").
|
|
10
|
+
* `argumentTypes` remain normalized for overload narrowing, while
|
|
11
|
+
* constraint predicates that need cv/ref/pointer shape read the parallel
|
|
12
|
+
* `argumentTypeClasses` sidecar. Unknown shapes must stay unknown rather
|
|
13
|
+
* than being guessed as incompatible.
|
|
15
14
|
*/
|
|
16
|
-
export type TypeClass = 'integral' | 'floating' | 'bool' | 'char' | 'string' | 'null' | 'class' | 'unknown';
|
|
15
|
+
export type TypeClass = 'integral' | 'floating' | 'bool' | 'char' | 'string' | 'null' | 'void' | 'enum' | 'class' | 'pointer' | 'reference' | 'unknown';
|
|
17
16
|
/**
|
|
18
17
|
* Classify a normalized C++ type token. The mapping mirrors the literal-
|
|
19
18
|
* inference table in `captures.ts:inferCppLiteralType` plus the std::
|
|
20
19
|
* normalization in `arity-metadata.ts:normalizeCppParamType`.
|
|
21
20
|
*
|
|
22
|
-
* Caller note: token
|
|
23
|
-
*
|
|
24
|
-
*
|
|
21
|
+
* Caller note: token should be normalized for overload matching. Enum
|
|
22
|
+
* tokens produced by the C++ adapter use the internal `enum:<Name>`
|
|
23
|
+
* prefix so `is_enum_v` does not have to guess that every user token is
|
|
24
|
+
* class-like.
|
|
25
25
|
*/
|
|
26
26
|
export declare function classifyType(token: string): TypeClass;
|
|
@@ -7,25 +7,29 @@
|
|
|
7
7
|
* the call-site inference in `captures.ts`) to one of the categories
|
|
8
8
|
* the `<type_traits>` predicate registry uses for SFINAE filtering.
|
|
9
9
|
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
*
|
|
14
|
-
* ("including any cv-qualified variants").
|
|
10
|
+
* `argumentTypes` remain normalized for overload narrowing, while
|
|
11
|
+
* constraint predicates that need cv/ref/pointer shape read the parallel
|
|
12
|
+
* `argumentTypeClasses` sidecar. Unknown shapes must stay unknown rather
|
|
13
|
+
* than being guessed as incompatible.
|
|
15
14
|
*/
|
|
16
15
|
/**
|
|
17
16
|
* Classify a normalized C++ type token. The mapping mirrors the literal-
|
|
18
17
|
* inference table in `captures.ts:inferCppLiteralType` plus the std::
|
|
19
18
|
* normalization in `arity-metadata.ts:normalizeCppParamType`.
|
|
20
19
|
*
|
|
21
|
-
* Caller note: token
|
|
22
|
-
*
|
|
23
|
-
*
|
|
20
|
+
* Caller note: token should be normalized for overload matching. Enum
|
|
21
|
+
* tokens produced by the C++ adapter use the internal `enum:<Name>`
|
|
22
|
+
* prefix so `is_enum_v` does not have to guess that every user token is
|
|
23
|
+
* class-like.
|
|
24
24
|
*/
|
|
25
25
|
export function classifyType(token) {
|
|
26
26
|
if (token.length === 0)
|
|
27
27
|
return 'unknown';
|
|
28
|
+
if (token.startsWith('enum:'))
|
|
29
|
+
return 'enum';
|
|
28
30
|
switch (token) {
|
|
31
|
+
case 'void':
|
|
32
|
+
return 'void';
|
|
29
33
|
case 'int':
|
|
30
34
|
return 'integral';
|
|
31
35
|
case 'double':
|
|
@@ -692,6 +692,7 @@ function pass5CollectReferences(matches, positionIndex, filePath, referenceSites
|
|
|
692
692
|
const explicitReceiver = extractExplicitReceiver(match);
|
|
693
693
|
const arity = extractArity(match);
|
|
694
694
|
const argumentTypes = extractArgumentTypes(match);
|
|
695
|
+
const argumentTypeClasses = parseJsonParameterTypeClassesCapture(match['@reference.parameter-type-classes']);
|
|
695
696
|
const site = {
|
|
696
697
|
name: nameCap.text,
|
|
697
698
|
atRange: anchor.range,
|
|
@@ -701,6 +702,7 @@ function pass5CollectReferences(matches, positionIndex, filePath, referenceSites
|
|
|
701
702
|
...(explicitReceiver !== undefined ? { explicitReceiver } : {}),
|
|
702
703
|
...(arity !== undefined ? { arity } : {}),
|
|
703
704
|
...(argumentTypes !== undefined ? { argumentTypes } : {}),
|
|
705
|
+
...(argumentTypeClasses !== undefined ? { argumentTypeClasses } : {}),
|
|
704
706
|
};
|
|
705
707
|
referenceSites.push(site);
|
|
706
708
|
}
|
|
@@ -806,9 +808,11 @@ const KNOWN_SUB_TAGS = new Set([
|
|
|
806
808
|
'@reference.receiver',
|
|
807
809
|
'@reference.arity',
|
|
808
810
|
'@reference.parameter-types',
|
|
811
|
+
'@reference.parameter-type-classes',
|
|
809
812
|
'@declaration.parameter-count',
|
|
810
813
|
'@declaration.required-parameter-count',
|
|
811
814
|
'@declaration.parameter-types',
|
|
815
|
+
'@declaration.parameter-type-classes',
|
|
812
816
|
'@declaration.template-constraints',
|
|
813
817
|
]);
|
|
814
818
|
/**
|
|
@@ -70,6 +70,7 @@ export declare function pickImplicitThisOverload(site: {
|
|
|
70
70
|
readonly name: string;
|
|
71
71
|
readonly arity?: number;
|
|
72
72
|
readonly argumentTypes?: readonly string[];
|
|
73
|
+
readonly argumentTypeClasses?: readonly import('../../../../_shared/index.js').ParameterTypeClass[];
|
|
73
74
|
}, scopes: ScopeResolutionIndexes, workspaceIndex: WorkspaceResolutionIndex, model: SemanticModel, hookCtx?: {
|
|
74
75
|
readonly conversionRankFn?: ConversionRankFn;
|
|
75
76
|
readonly constraintCompatibility?: ScopeResolver['constraintCompatibility'];
|
|
@@ -72,6 +72,7 @@ export function emitFreeCallFallback(graph, scopes, parsedFiles, nodeLookup, _re
|
|
|
72
72
|
const allCallables = findAllCallableBindingsInScope(site.inScope, site.name, scopes);
|
|
73
73
|
if (allCallables.length > 1) {
|
|
74
74
|
const narrowed = narrowOverloadCandidates(allCallables, site.arity, site.argumentTypes, {
|
|
75
|
+
argumentTypeClasses: site.argumentTypeClasses,
|
|
75
76
|
conversionRankFn: options.conversionRankFn,
|
|
76
77
|
constraintCompatibility: options.constraintCompatibility,
|
|
77
78
|
});
|
|
@@ -126,6 +127,7 @@ export function emitFreeCallFallback(graph, scopes, parsedFiles, nodeLookup, _re
|
|
|
126
127
|
}
|
|
127
128
|
else {
|
|
128
129
|
const narrowed = narrowOverloadCandidates(ordinary, site.arity, site.argumentTypes, {
|
|
130
|
+
argumentTypeClasses: site.argumentTypeClasses,
|
|
129
131
|
conversionRankFn: options.conversionRankFn,
|
|
130
132
|
constraintCompatibility: options.constraintCompatibility,
|
|
131
133
|
});
|
|
@@ -164,6 +166,7 @@ export function emitFreeCallFallback(graph, scopes, parsedFiles, nodeLookup, _re
|
|
|
164
166
|
push(ordinary);
|
|
165
167
|
push(adl);
|
|
166
168
|
const narrowed = narrowOverloadCandidates(merged, site.arity, site.argumentTypes, {
|
|
169
|
+
argumentTypeClasses: site.argumentTypeClasses,
|
|
167
170
|
conversionRankFn: options.conversionRankFn,
|
|
168
171
|
constraintCompatibility: options.constraintCompatibility,
|
|
169
172
|
});
|
|
@@ -427,6 +430,7 @@ export function pickImplicitThisOverload(site, scopes, workspaceIndex, model, ho
|
|
|
427
430
|
// disambiguating signal) leaves the call unresolved rather than
|
|
428
431
|
// routing to an arbitrary first overload by registration order.
|
|
429
432
|
const candidates = narrowOverloadCandidates(overloads, site.arity, site.argumentTypes, {
|
|
433
|
+
argumentTypeClasses: site.argumentTypeClasses,
|
|
430
434
|
conversionRankFn: hookCtx?.conversionRankFn,
|
|
431
435
|
constraintCompatibility: hookCtx?.constraintCompatibility,
|
|
432
436
|
});
|
|
@@ -59,6 +59,8 @@ export type ConversionRankFn = (argType: string, paramType: string) => number;
|
|
|
59
59
|
* undefined preserves the legacy arity + exact-type behavior.
|
|
60
60
|
*/
|
|
61
61
|
export interface OverloadNarrowingHookCtx {
|
|
62
|
+
/** Shape-preserving per-argument sidecar aligned with `argTypes`. */
|
|
63
|
+
readonly argumentTypeClasses?: ConstraintContext['argumentTypeClasses'];
|
|
62
64
|
/** Conversion-rank scoring fallback (step 4b). Engages when the
|
|
63
65
|
* exact-type filter rejects every candidate. */
|
|
64
66
|
readonly conversionRankFn?: ConversionRankFn;
|
|
@@ -118,7 +118,14 @@ export function narrowOverloadCandidates(overloads, argCount, argTypes, hookCtx)
|
|
|
118
118
|
// than emitting a wrong edge.
|
|
119
119
|
if (hookCtx?.constraintCompatibility !== undefined && argCount !== undefined) {
|
|
120
120
|
const callsite = { arity: argCount };
|
|
121
|
-
const ctx = argTypes !== undefined
|
|
121
|
+
const ctx = argTypes !== undefined
|
|
122
|
+
? {
|
|
123
|
+
argumentTypes: argTypes,
|
|
124
|
+
...(hookCtx.argumentTypeClasses !== undefined
|
|
125
|
+
? { argumentTypeClasses: hookCtx.argumentTypeClasses }
|
|
126
|
+
: {}),
|
|
127
|
+
}
|
|
128
|
+
: {};
|
|
122
129
|
result = result.filter((def) => {
|
|
123
130
|
if (def.templateConstraints === undefined)
|
|
124
131
|
return true;
|
|
@@ -250,6 +250,7 @@ export function emitReceiverBoundCalls(graph, scopes, parsedFiles, nodeLookup, h
|
|
|
250
250
|
const methodOverloads = model.methods.lookupAllByOwner(ownerId, memberName);
|
|
251
251
|
if (methodOverloads.length > 0) {
|
|
252
252
|
const narrowed = narrowOverloadCandidates(methodOverloads, site.arity, site.argumentTypes, {
|
|
253
|
+
argumentTypeClasses: site.argumentTypeClasses,
|
|
253
254
|
conversionRankFn: provider.conversionRankFn,
|
|
254
255
|
constraintCompatibility: provider.constraintCompatibility,
|
|
255
256
|
});
|
|
@@ -532,6 +533,7 @@ function pickOverload(ownerId, memberName, site, model, provider) {
|
|
|
532
533
|
if (overloads.length === 1)
|
|
533
534
|
return overloads[0];
|
|
534
535
|
const candidates = narrowOverloadCandidates(overloads, site.arity, site.argumentTypes, {
|
|
536
|
+
argumentTypeClasses: site.argumentTypeClasses,
|
|
535
537
|
conversionRankFn: provider.conversionRankFn,
|
|
536
538
|
constraintCompatibility: provider.constraintCompatibility,
|
|
537
539
|
});
|
package/package.json
CHANGED