@suss/resolution 0.21.0 → 0.22.0
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/README.md +38 -0
- package/dist/index.cjs +452 -362
- package/dist/index.d.cts +78 -2
- package/dist/index.d.ts +78 -2
- package/dist/index.js +118 -31
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -31,9 +31,12 @@ __export(index_exports, {
|
|
|
31
31
|
agreedMountPrefix: () => agreedMountPrefix,
|
|
32
32
|
checkFactContract: () => checkFactContract,
|
|
33
33
|
explainResolutionProof: () => explainResolutionProof,
|
|
34
|
+
explainResolvedKey: () => explainResolvedKey,
|
|
34
35
|
joinMountedPath: () => joinMountedPath,
|
|
35
36
|
mountPathsOf: () => mountPathsOf,
|
|
36
|
-
|
|
37
|
+
placeholderValues: () => placeholderValues,
|
|
38
|
+
renderExplanation: () => renderExplanation,
|
|
39
|
+
singleAnswers: () => singleAnswers
|
|
37
40
|
});
|
|
38
41
|
module.exports = __toCommonJS(index_exports);
|
|
39
42
|
|
|
@@ -516,325 +519,424 @@ function pathsOf(edges, memo, childId, visiting) {
|
|
|
516
519
|
return result;
|
|
517
520
|
}
|
|
518
521
|
|
|
519
|
-
// src/
|
|
522
|
+
// src/session.ts
|
|
520
523
|
var import_datalog2 = require("@suss/datalog");
|
|
521
|
-
|
|
524
|
+
function explainResolvedKey(options) {
|
|
525
|
+
const { db, rules, key, locate, displayPath } = options;
|
|
526
|
+
const proofDb = new import_datalog2.Database();
|
|
527
|
+
let baseFacts = 0;
|
|
528
|
+
for (const relation of db.relationNames()) {
|
|
529
|
+
for (const tuple of db.facts(relation)) {
|
|
530
|
+
proofDb.add(relation, tuple);
|
|
531
|
+
baseFacts++;
|
|
532
|
+
}
|
|
533
|
+
}
|
|
534
|
+
const started = performance.now();
|
|
535
|
+
(0, import_datalog2.evaluate)(proofDb, rules, import_datalog2.witnesses);
|
|
536
|
+
const evaluateMs = performance.now() - started;
|
|
537
|
+
const derivedFacts = proofDb.relationNames().reduce((count, relation) => count + proofDb.size(relation), 0) - baseFacts;
|
|
538
|
+
const targets = new Set(
|
|
539
|
+
proofDb.lookup("resolves", 0, key).map((tuple) => String(tuple[1]))
|
|
540
|
+
);
|
|
541
|
+
if (targets.size !== 1) {
|
|
542
|
+
return null;
|
|
543
|
+
}
|
|
544
|
+
const target = [...targets][0];
|
|
545
|
+
const proof = (0, import_datalog2.proofOf)(
|
|
546
|
+
proofDb,
|
|
547
|
+
"resolves",
|
|
548
|
+
[key, target],
|
|
549
|
+
options.maxDepth === void 0 ? {} : { maxDepth: options.maxDepth }
|
|
550
|
+
);
|
|
551
|
+
const describe = (atom) => {
|
|
552
|
+
const location = locate(String(atom));
|
|
553
|
+
return location === null ? displayPath(String(atom)) : `${location.name} (${location.file}:${location.line})`;
|
|
554
|
+
};
|
|
555
|
+
const explanation = explainResolutionProof(proof, {
|
|
556
|
+
describe,
|
|
557
|
+
...options.phrases === void 0 ? {} : { phrases: options.phrases }
|
|
558
|
+
});
|
|
559
|
+
if (explanation === null) {
|
|
560
|
+
return null;
|
|
561
|
+
}
|
|
562
|
+
const targetLocation = locate(target);
|
|
563
|
+
if (targetLocation === null) {
|
|
564
|
+
return null;
|
|
565
|
+
}
|
|
566
|
+
return {
|
|
567
|
+
explanation,
|
|
568
|
+
chain: explanation.atoms.map(describe),
|
|
569
|
+
lines: renderExplanation(explanation, describe),
|
|
570
|
+
target: targetLocation,
|
|
571
|
+
stats: { baseFacts, derivedFacts, evaluateMs }
|
|
572
|
+
};
|
|
573
|
+
}
|
|
574
|
+
|
|
575
|
+
// src/singleAnswer.ts
|
|
576
|
+
var NO_PLACEHOLDERS = /* @__PURE__ */ new Set();
|
|
577
|
+
function singleAnswers(rows, placeholders = NO_PLACEHOLDERS) {
|
|
578
|
+
const candidates = /* @__PURE__ */ new Map();
|
|
579
|
+
for (const row of rows) {
|
|
580
|
+
const key = String(row[0]);
|
|
581
|
+
const answer = String(row[1]);
|
|
582
|
+
if (answer === key) {
|
|
583
|
+
continue;
|
|
584
|
+
}
|
|
585
|
+
const set = candidates.get(key) ?? /* @__PURE__ */ new Set();
|
|
586
|
+
set.add(answer);
|
|
587
|
+
candidates.set(key, set);
|
|
588
|
+
}
|
|
589
|
+
const settled = /* @__PURE__ */ new Map();
|
|
590
|
+
for (const [key, set] of candidates) {
|
|
591
|
+
const answers = withoutPlaceholders(set, placeholders);
|
|
592
|
+
if (answers.length === 1) {
|
|
593
|
+
settled.set(key, answers[0]);
|
|
594
|
+
}
|
|
595
|
+
}
|
|
596
|
+
return settled;
|
|
597
|
+
}
|
|
598
|
+
function placeholderValues(db) {
|
|
599
|
+
return new Set(db.facts("placeholderValue").map((row) => String(row[0])));
|
|
600
|
+
}
|
|
601
|
+
function withoutPlaceholders(answers, placeholders) {
|
|
602
|
+
const kept = [...answers].filter((answer) => !placeholders.has(answer));
|
|
603
|
+
if (kept.length === 0) {
|
|
604
|
+
return [...answers];
|
|
605
|
+
}
|
|
606
|
+
return kept;
|
|
607
|
+
}
|
|
608
|
+
|
|
609
|
+
// src/index.ts
|
|
610
|
+
var import_datalog3 = require("@suss/datalog");
|
|
611
|
+
var VALUE_STEP = (0, import_datalog3.constant)("value");
|
|
522
612
|
var NAMESPACE_IMPORT_NAME = "*";
|
|
523
|
-
var NAMESPACE_IMPORT = (0,
|
|
524
|
-
var RESULT_STEP = (0,
|
|
613
|
+
var NAMESPACE_IMPORT = (0, import_datalog3.constant)(NAMESPACE_IMPORT_NAME);
|
|
614
|
+
var RESULT_STEP = (0, import_datalog3.constant)("result");
|
|
525
615
|
var RESOLUTION_RULES = [
|
|
526
616
|
// Aliasing: const x = y, or an identifier referencing a declaration.
|
|
527
617
|
// A language with a hop of its own, like JavaScript's `.bind`, states
|
|
528
618
|
// it as a step too, or every question but `comesTo` misses it.
|
|
529
|
-
(0,
|
|
619
|
+
(0, import_datalog3.rule)(
|
|
530
620
|
"stepsTo",
|
|
531
|
-
[(0,
|
|
532
|
-
[(0,
|
|
621
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), VALUE_STEP],
|
|
622
|
+
[(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"))],
|
|
533
623
|
"alias"
|
|
534
624
|
),
|
|
535
625
|
// A name written more than once has the value the last write left
|
|
536
626
|
// there. The adapter works out which write that is and stays quiet
|
|
537
627
|
// when control flow decides, so such a name steps nowhere at all.
|
|
538
|
-
(0,
|
|
628
|
+
(0, import_datalog3.rule)(
|
|
539
629
|
"stepsTo",
|
|
540
|
-
[(0,
|
|
541
|
-
[(0,
|
|
630
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), VALUE_STEP],
|
|
631
|
+
[(0, import_datalog3.lit)("endsHolding", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"))],
|
|
542
632
|
"last write"
|
|
543
633
|
),
|
|
544
634
|
// A fallback says the value is one of its branches, so each branch is
|
|
545
635
|
// a step. A branch that resolves to nothing makes no claim, and two
|
|
546
636
|
// branches resolving to different things fail the single-answer policy.
|
|
547
|
-
(0,
|
|
637
|
+
(0, import_datalog3.rule)(
|
|
548
638
|
"stepsTo",
|
|
549
|
-
[(0,
|
|
550
|
-
[(0,
|
|
639
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("b"), VALUE_STEP],
|
|
640
|
+
[(0, import_datalog3.lit)("fallbackBranch", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("b"))],
|
|
551
641
|
"fallback"
|
|
552
642
|
),
|
|
553
643
|
// An import steps to what the module exports under that name.
|
|
554
|
-
(0,
|
|
644
|
+
(0, import_datalog3.rule)(
|
|
555
645
|
"stepsTo",
|
|
556
|
-
[(0,
|
|
646
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("value"), VALUE_STEP],
|
|
557
647
|
[
|
|
558
|
-
(0,
|
|
559
|
-
(0,
|
|
648
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")),
|
|
649
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value"))
|
|
560
650
|
],
|
|
561
651
|
"import"
|
|
562
652
|
),
|
|
563
653
|
// A parameter steps to what a call passes it. A function called from
|
|
564
654
|
// several places leaves its parameter with more than one value, and a
|
|
565
655
|
// caller that needs those apart asks `paramAt`.
|
|
566
|
-
(0,
|
|
656
|
+
(0, import_datalog3.rule)(
|
|
567
657
|
"stepsTo",
|
|
568
|
-
[(0,
|
|
569
|
-
[(0,
|
|
658
|
+
[(0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("a"), VALUE_STEP],
|
|
659
|
+
[(0, import_datalog3.lit)("passesArgument", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("a"))],
|
|
570
660
|
"argument"
|
|
571
661
|
),
|
|
572
662
|
// Reading a property steps to what the object contains under that
|
|
573
663
|
// name, whichever way the object arrived: `routes.list` off a name,
|
|
574
664
|
// or `make(body).handle` off a call.
|
|
575
|
-
(0,
|
|
665
|
+
(0, import_datalog3.rule)(
|
|
576
666
|
"stepsTo",
|
|
577
|
-
[(0,
|
|
667
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("held"), VALUE_STEP],
|
|
578
668
|
[
|
|
579
|
-
(0,
|
|
580
|
-
(0,
|
|
581
|
-
(0,
|
|
669
|
+
(0, import_datalog3.lit)("readsProperty", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("n")),
|
|
670
|
+
(0, import_datalog3.lit)("objectOf", (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("obj")),
|
|
671
|
+
(0, import_datalog3.lit)("contains", (0, import_datalog3.variable)("obj"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("held"))
|
|
582
672
|
],
|
|
583
673
|
"property read"
|
|
584
674
|
),
|
|
585
675
|
// Calling a class makes one of it, so the call steps to the class and
|
|
586
676
|
// a method read off the result is the one the class declares. The
|
|
587
677
|
// caveat below is about a factory function, and a class is not one.
|
|
588
|
-
(0,
|
|
678
|
+
(0, import_datalog3.rule)(
|
|
589
679
|
"stepsTo",
|
|
590
|
-
[(0,
|
|
680
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("cls"), VALUE_STEP],
|
|
591
681
|
[
|
|
592
|
-
(0,
|
|
593
|
-
(0,
|
|
594
|
-
(0,
|
|
682
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c")),
|
|
683
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("cls")),
|
|
684
|
+
(0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("cls"))
|
|
595
685
|
],
|
|
596
686
|
"class instance"
|
|
597
687
|
),
|
|
598
688
|
// Wrapper transparency, derived: calling a factory that returns a
|
|
599
689
|
// function which calls its parameter k steps to argument k.
|
|
600
|
-
(0,
|
|
690
|
+
(0, import_datalog3.rule)(
|
|
601
691
|
"stepsTo",
|
|
602
|
-
[(0,
|
|
692
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("a"), VALUE_STEP],
|
|
603
693
|
[
|
|
604
|
-
(0,
|
|
605
|
-
(0,
|
|
606
|
-
(0,
|
|
607
|
-
(0,
|
|
694
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c")),
|
|
695
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f")),
|
|
696
|
+
(0, import_datalog3.lit)("unwraps", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k")),
|
|
697
|
+
(0, import_datalog3.lit)("callArg", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("a"))
|
|
608
698
|
],
|
|
609
699
|
"factory unwrap"
|
|
610
700
|
),
|
|
611
701
|
// Wrapper transparency, declared: a pack says this callee wraps
|
|
612
702
|
// argument k. The callee has to come from the library the pack said,
|
|
613
703
|
// so a local object spelled the same way is not mistaken for it.
|
|
614
|
-
(0,
|
|
704
|
+
(0, import_datalog3.rule)(
|
|
615
705
|
"stepsTo",
|
|
616
|
-
[(0,
|
|
706
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("a"), VALUE_STEP],
|
|
617
707
|
[
|
|
618
|
-
(0,
|
|
619
|
-
(0,
|
|
620
|
-
(0,
|
|
621
|
-
(0,
|
|
622
|
-
(0,
|
|
708
|
+
(0, import_datalog3.lit)("calleeName", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("n")),
|
|
709
|
+
(0, import_datalog3.lit)("unwrapsByName", (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("k")),
|
|
710
|
+
(0, import_datalog3.lit)("wrapperModule", (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m")),
|
|
711
|
+
(0, import_datalog3.lit)("calleeOrigin", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("m")),
|
|
712
|
+
(0, import_datalog3.lit)("callArg", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("a"))
|
|
623
713
|
],
|
|
624
714
|
"declared wrapper"
|
|
625
715
|
),
|
|
626
716
|
// The one step that runs a function forwards: a call steps to what
|
|
627
717
|
// the function it invokes returns.
|
|
628
|
-
(0,
|
|
718
|
+
(0, import_datalog3.rule)(
|
|
629
719
|
"stepsTo",
|
|
630
|
-
[(0,
|
|
631
|
-
[(0,
|
|
720
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("ret"), RESULT_STEP],
|
|
721
|
+
[(0, import_datalog3.lit)("invokes", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")), (0, import_datalog3.lit)("returnsValue", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("ret"))],
|
|
632
722
|
"call result"
|
|
633
723
|
),
|
|
634
|
-
// Where a walk gets to, and whether it ran a call on the way.
|
|
635
|
-
//
|
|
636
|
-
//
|
|
637
|
-
(0,
|
|
724
|
+
// Where a walk gets to, and whether it ran a call on the way. The walk
|
|
725
|
+
// so far comes first, so demand stays on the value asked about; the
|
|
726
|
+
// README says what the other order cost.
|
|
727
|
+
(0, import_datalog3.rule)(
|
|
638
728
|
"reaches",
|
|
639
|
-
[(0,
|
|
640
|
-
[(0,
|
|
729
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), (0, import_datalog3.variable)("kind")],
|
|
730
|
+
[(0, import_datalog3.lit)("stepsTo", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), (0, import_datalog3.variable)("kind"))]
|
|
641
731
|
),
|
|
642
|
-
(0,
|
|
732
|
+
(0, import_datalog3.rule)(
|
|
643
733
|
"reaches",
|
|
644
|
-
[(0,
|
|
734
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), (0, import_datalog3.variable)("kind")],
|
|
645
735
|
[
|
|
646
|
-
(0,
|
|
647
|
-
(0,
|
|
736
|
+
(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), VALUE_STEP),
|
|
737
|
+
(0, import_datalog3.lit)("stepsTo", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"), (0, import_datalog3.variable)("kind"))
|
|
648
738
|
]
|
|
649
739
|
),
|
|
650
|
-
// Two rules rather than one leaving the
|
|
651
|
-
//
|
|
740
|
+
// Two rules rather than one leaving the next step's kind free. A free
|
|
741
|
+
// kind is a second question about the same relation, and a
|
|
652
742
|
// demand-driven run then derives both to answer either.
|
|
653
|
-
(0,
|
|
743
|
+
(0, import_datalog3.rule)(
|
|
654
744
|
"reaches",
|
|
655
|
-
[(0,
|
|
745
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), RESULT_STEP],
|
|
656
746
|
[
|
|
657
|
-
(0,
|
|
658
|
-
(0,
|
|
747
|
+
(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), RESULT_STEP),
|
|
748
|
+
(0, import_datalog3.lit)("stepsTo", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"), VALUE_STEP)
|
|
659
749
|
]
|
|
660
750
|
),
|
|
661
|
-
(0,
|
|
751
|
+
(0, import_datalog3.rule)(
|
|
662
752
|
"reaches",
|
|
663
|
-
[(0,
|
|
753
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), RESULT_STEP],
|
|
664
754
|
[
|
|
665
|
-
(0,
|
|
666
|
-
(0,
|
|
755
|
+
(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), RESULT_STEP),
|
|
756
|
+
(0, import_datalog3.lit)("stepsTo", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"), RESULT_STEP)
|
|
667
757
|
]
|
|
668
758
|
),
|
|
669
759
|
// What a value comes down to: the walk that never ran a call, stopped
|
|
670
760
|
// at a function or an object. Something already written out comes to
|
|
671
761
|
// itself, and every other walk ends at one of those.
|
|
672
|
-
(0,
|
|
673
|
-
(0,
|
|
674
|
-
(0,
|
|
762
|
+
(0, import_datalog3.rule)("comesTo", [(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("x")], [(0, import_datalog3.lit)("func", (0, import_datalog3.variable)("x"))]),
|
|
763
|
+
(0, import_datalog3.rule)("comesTo", [(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("x")], [(0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("x"))]),
|
|
764
|
+
(0, import_datalog3.rule)(
|
|
675
765
|
"comesTo",
|
|
676
|
-
[(0,
|
|
677
|
-
[(0,
|
|
766
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
767
|
+
[(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), VALUE_STEP), (0, import_datalog3.lit)("func", (0, import_datalog3.variable)("z"))]
|
|
678
768
|
),
|
|
679
|
-
(0,
|
|
769
|
+
(0, import_datalog3.rule)(
|
|
680
770
|
"comesTo",
|
|
681
|
-
[(0,
|
|
682
|
-
[(0,
|
|
771
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
772
|
+
[(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), VALUE_STEP), (0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("z"))]
|
|
683
773
|
),
|
|
684
774
|
// The same stopping condition, for the walk that ran a call. A call
|
|
685
775
|
// gets no `comesTo` answer on purpose: coming back with what a
|
|
686
776
|
// factory returned would fight the unwrapping answer.
|
|
687
|
-
(0,
|
|
777
|
+
(0, import_datalog3.rule)(
|
|
688
778
|
"givesBack",
|
|
689
|
-
[(0,
|
|
690
|
-
[(0,
|
|
779
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
780
|
+
[(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), RESULT_STEP), (0, import_datalog3.lit)("func", (0, import_datalog3.variable)("z"))]
|
|
691
781
|
),
|
|
692
|
-
(0,
|
|
782
|
+
(0, import_datalog3.rule)(
|
|
693
783
|
"givesBack",
|
|
694
|
-
[(0,
|
|
695
|
-
[(0,
|
|
784
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
785
|
+
[(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), RESULT_STEP), (0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("z"))]
|
|
696
786
|
),
|
|
697
787
|
// Following a value to the expression it is written as, whatever kind
|
|
698
788
|
// that is. A GraphQL document is neither a function nor an object, so
|
|
699
789
|
// `comesTo` never reaches one.
|
|
700
|
-
(0,
|
|
701
|
-
(0,
|
|
702
|
-
(0,
|
|
790
|
+
(0, import_datalog3.rule)("isWrittenAs", [(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("x")], [(0, import_datalog3.lit)("writtenValue", (0, import_datalog3.variable)("x"))]),
|
|
791
|
+
(0, import_datalog3.rule)("isWrittenAs", [(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("x")], [(0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("x"))]),
|
|
792
|
+
(0, import_datalog3.rule)(
|
|
793
|
+
"isWrittenAs",
|
|
794
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
795
|
+
[(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), VALUE_STEP), (0, import_datalog3.lit)("writtenValue", (0, import_datalog3.variable)("z"))]
|
|
796
|
+
),
|
|
797
|
+
(0, import_datalog3.rule)(
|
|
703
798
|
"isWrittenAs",
|
|
704
|
-
[(0,
|
|
705
|
-
[(0,
|
|
799
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
800
|
+
[(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), VALUE_STEP), (0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("z"))]
|
|
706
801
|
),
|
|
707
|
-
|
|
802
|
+
// A call is written as whatever its callee's return value is written
|
|
803
|
+
// as. Unlike `comesTo`, this has nothing to protect: which expression
|
|
804
|
+
// a value was written as does not compete with unwrapping it.
|
|
805
|
+
(0, import_datalog3.rule)(
|
|
708
806
|
"isWrittenAs",
|
|
709
|
-
[(0,
|
|
710
|
-
[
|
|
807
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
808
|
+
[
|
|
809
|
+
(0, import_datalog3.lit)("invokes", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("f")),
|
|
810
|
+
(0, import_datalog3.lit)("returnsValue", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("ret")),
|
|
811
|
+
(0, import_datalog3.lit)("isWrittenAs", (0, import_datalog3.variable)("ret"), (0, import_datalog3.variable)("z"))
|
|
812
|
+
]
|
|
711
813
|
),
|
|
712
814
|
// What one call site put in a parameter, told apart from what the
|
|
713
815
|
// other callers passed.
|
|
714
|
-
(0,
|
|
816
|
+
(0, import_datalog3.rule)(
|
|
715
817
|
"paramAt",
|
|
716
|
-
[(0,
|
|
818
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("z")],
|
|
717
819
|
[
|
|
718
|
-
(0,
|
|
719
|
-
(0,
|
|
820
|
+
(0, import_datalog3.lit)("passesArgument", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("a")),
|
|
821
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("a"), (0, import_datalog3.variable)("z"))
|
|
720
822
|
]
|
|
721
823
|
),
|
|
722
824
|
// An argument arriving at the parameter it is passed to, by position
|
|
723
825
|
// or by the name the caller wrote, keeping the call it went through
|
|
724
826
|
// so `paramAt` can tell two call sites apart.
|
|
725
|
-
(0,
|
|
827
|
+
(0, import_datalog3.rule)(
|
|
726
828
|
"passesArgument",
|
|
727
|
-
[(0,
|
|
829
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("a")],
|
|
728
830
|
[
|
|
729
|
-
(0,
|
|
730
|
-
(0,
|
|
731
|
-
(0,
|
|
831
|
+
(0, import_datalog3.lit)("paramOf", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("p")),
|
|
832
|
+
(0, import_datalog3.lit)("callsFunction", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")),
|
|
833
|
+
(0, import_datalog3.lit)("callArg", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("a"))
|
|
732
834
|
]
|
|
733
835
|
),
|
|
734
|
-
(0,
|
|
836
|
+
(0, import_datalog3.rule)(
|
|
735
837
|
"passesArgument",
|
|
736
|
-
[(0,
|
|
838
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("a")],
|
|
737
839
|
[
|
|
738
|
-
(0,
|
|
739
|
-
(0,
|
|
740
|
-
(0,
|
|
840
|
+
(0, import_datalog3.lit)("paramNamed", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("p")),
|
|
841
|
+
(0, import_datalog3.lit)("callsFunction", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")),
|
|
842
|
+
(0, import_datalog3.lit)("callKeywordArg", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("a"))
|
|
741
843
|
]
|
|
742
844
|
),
|
|
743
845
|
// Which module's export a re-exported name forwards to, however
|
|
744
846
|
// many barrels deep the forwarding runs.
|
|
745
|
-
(0,
|
|
847
|
+
(0, import_datalog3.rule)(
|
|
746
848
|
"moduleForwards",
|
|
747
|
-
[(0,
|
|
748
|
-
[(0,
|
|
849
|
+
[(0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2")],
|
|
850
|
+
[(0, import_datalog3.lit)("reExports", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2"))]
|
|
749
851
|
),
|
|
750
|
-
(0,
|
|
852
|
+
(0, import_datalog3.rule)(
|
|
751
853
|
"moduleForwards",
|
|
752
|
-
[(0,
|
|
854
|
+
[(0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m3"), (0, import_datalog3.variable)("n3")],
|
|
753
855
|
[
|
|
754
|
-
(0,
|
|
755
|
-
(0,
|
|
856
|
+
(0, import_datalog3.lit)("reExports", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2")),
|
|
857
|
+
(0, import_datalog3.lit)("moduleForwards", (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2"), (0, import_datalog3.variable)("m3"), (0, import_datalog3.variable)("n3"))
|
|
756
858
|
]
|
|
757
859
|
),
|
|
758
860
|
// What a module exports: directly, or through re-export chains.
|
|
759
|
-
(0,
|
|
861
|
+
(0, import_datalog3.rule)(
|
|
760
862
|
"moduleExport",
|
|
761
|
-
[(0,
|
|
762
|
-
[(0,
|
|
863
|
+
[(0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value")],
|
|
864
|
+
[(0, import_datalog3.lit)("exportsAs", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value"))],
|
|
763
865
|
"export"
|
|
764
866
|
),
|
|
765
|
-
(0,
|
|
867
|
+
(0, import_datalog3.rule)(
|
|
766
868
|
"moduleExport",
|
|
767
|
-
[(0,
|
|
869
|
+
[(0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value")],
|
|
768
870
|
[
|
|
769
|
-
(0,
|
|
770
|
-
(0,
|
|
871
|
+
(0, import_datalog3.lit)("reExports", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2")),
|
|
872
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2"), (0, import_datalog3.variable)("value"))
|
|
771
873
|
],
|
|
772
874
|
"re-export"
|
|
773
875
|
),
|
|
774
|
-
(0,
|
|
876
|
+
(0, import_datalog3.rule)(
|
|
775
877
|
"moduleExport",
|
|
776
|
-
[(0,
|
|
878
|
+
[(0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value")],
|
|
777
879
|
[
|
|
778
|
-
(0,
|
|
779
|
-
(0,
|
|
880
|
+
(0, import_datalog3.lit)("reExportsAll", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("m2")),
|
|
881
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value"))
|
|
780
882
|
],
|
|
781
883
|
"re-export all"
|
|
782
884
|
),
|
|
783
885
|
// The function a call runs, written from the call's side because a
|
|
784
886
|
// caller asking what a call gives back has the call in hand.
|
|
785
|
-
(0,
|
|
887
|
+
(0, import_datalog3.rule)(
|
|
786
888
|
"invokes",
|
|
787
|
-
[(0,
|
|
788
|
-
[(0,
|
|
889
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")],
|
|
890
|
+
[(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c")), (0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f"))]
|
|
789
891
|
),
|
|
790
892
|
// The callee is itself a call: `daoBuilder()()`.
|
|
791
|
-
(0,
|
|
893
|
+
(0, import_datalog3.rule)(
|
|
792
894
|
"invokes",
|
|
793
|
-
[(0,
|
|
794
|
-
[(0,
|
|
895
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")],
|
|
896
|
+
[(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c")), (0, import_datalog3.lit)("givesBack", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f"))]
|
|
795
897
|
),
|
|
796
898
|
// The object an expression refers to: a name through `comesTo`, a
|
|
797
899
|
// factory call through what it gives back. Naming the step is what
|
|
798
900
|
// makes `routes.list` and `make(body).handle` one rule.
|
|
799
|
-
(0,
|
|
901
|
+
(0, import_datalog3.rule)(
|
|
800
902
|
"objectOf",
|
|
801
|
-
[(0,
|
|
802
|
-
[(0,
|
|
903
|
+
[(0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("obj")],
|
|
904
|
+
[(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("obj")), (0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("obj"))]
|
|
803
905
|
),
|
|
804
|
-
(0,
|
|
906
|
+
(0, import_datalog3.rule)(
|
|
805
907
|
"objectOf",
|
|
806
|
-
[(0,
|
|
807
|
-
[(0,
|
|
908
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("obj")],
|
|
909
|
+
[(0, import_datalog3.lit)("givesBack", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("obj")), (0, import_datalog3.lit)("objectValue", (0, import_datalog3.variable)("obj"))]
|
|
808
910
|
),
|
|
809
911
|
// Which calls a function, found by the name the call is written as
|
|
810
912
|
// rather than by resolving every callee in the project. A caller knows
|
|
811
913
|
// the function and wants its call sites, so both of these start from
|
|
812
914
|
// the function. Starting from `call` instead asks what every call in
|
|
813
915
|
// the project imports, which was 72% of everything derived.
|
|
814
|
-
(0,
|
|
916
|
+
(0, import_datalog3.rule)(
|
|
815
917
|
"callsFunction",
|
|
816
|
-
[(0,
|
|
817
|
-
[(0,
|
|
918
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")],
|
|
919
|
+
[(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f")), (0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c"))]
|
|
818
920
|
),
|
|
819
|
-
(0,
|
|
921
|
+
(0, import_datalog3.rule)(
|
|
820
922
|
"callsFunction",
|
|
821
|
-
[(0,
|
|
923
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")],
|
|
822
924
|
[
|
|
823
|
-
(0,
|
|
824
|
-
(0,
|
|
825
|
-
(0,
|
|
925
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("f")),
|
|
926
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")),
|
|
927
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c"))
|
|
826
928
|
]
|
|
827
929
|
),
|
|
828
930
|
// The same, for a language whose adapter writes the import down as a
|
|
829
931
|
// declaration and the call's callee as the name referring to it.
|
|
830
|
-
(0,
|
|
932
|
+
(0, import_datalog3.rule)(
|
|
831
933
|
"callsFunction",
|
|
832
|
-
[(0,
|
|
934
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("f")],
|
|
833
935
|
[
|
|
834
|
-
(0,
|
|
835
|
-
(0,
|
|
836
|
-
(0,
|
|
837
|
-
(0,
|
|
936
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("f")),
|
|
937
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("d"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")),
|
|
938
|
+
(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("d")),
|
|
939
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c"))
|
|
838
940
|
]
|
|
839
941
|
),
|
|
840
942
|
// What an object contains, its base class included, so a method the base
|
|
@@ -842,47 +944,47 @@ var RESOLUTION_RULES = [
|
|
|
842
944
|
// declare gives two, and the caller decides. This is its own relation
|
|
843
945
|
// rather than more `holdsProperty`, which stays something an adapter
|
|
844
946
|
// states and the rules only read.
|
|
845
|
-
(0,
|
|
947
|
+
(0, import_datalog3.rule)(
|
|
846
948
|
"contains",
|
|
847
|
-
[(0,
|
|
848
|
-
[(0,
|
|
949
|
+
[(0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("held")],
|
|
950
|
+
[(0, import_datalog3.lit)("holdsProperty", (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("held"))]
|
|
849
951
|
),
|
|
850
|
-
(0,
|
|
952
|
+
(0, import_datalog3.rule)(
|
|
851
953
|
"contains",
|
|
852
|
-
[(0,
|
|
954
|
+
[(0, import_datalog3.variable)("cls"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("held")],
|
|
853
955
|
[
|
|
854
|
-
(0,
|
|
855
|
-
(0,
|
|
856
|
-
(0,
|
|
956
|
+
(0, import_datalog3.lit)("extends", (0, import_datalog3.variable)("cls"), (0, import_datalog3.variable)("base")),
|
|
957
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("base"), (0, import_datalog3.variable)("baseCls")),
|
|
958
|
+
(0, import_datalog3.lit)("contains", (0, import_datalog3.variable)("baseCls"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("held"))
|
|
857
959
|
]
|
|
858
960
|
),
|
|
859
961
|
// Which function a factory returns, and which of its parameters that
|
|
860
962
|
// function calls: together they are what makes it a wrapper.
|
|
861
|
-
(0,
|
|
963
|
+
(0, import_datalog3.rule)(
|
|
862
964
|
"returnsFunc",
|
|
863
|
-
[(0,
|
|
965
|
+
[(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("g")],
|
|
864
966
|
[
|
|
865
|
-
(0,
|
|
866
|
-
(0,
|
|
867
|
-
(0,
|
|
967
|
+
(0, import_datalog3.lit)("returnsValue", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("value")),
|
|
968
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("value"), (0, import_datalog3.variable)("g")),
|
|
969
|
+
(0, import_datalog3.lit)("func", (0, import_datalog3.variable)("g"))
|
|
868
970
|
]
|
|
869
971
|
),
|
|
870
972
|
// A call made by a nested closure counts as made by the function
|
|
871
973
|
// that declares it; the closure runs as part of that function.
|
|
872
|
-
(0,
|
|
873
|
-
(0,
|
|
974
|
+
(0, import_datalog3.rule)("bodyCallsDeep", [(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("c")], [(0, import_datalog3.lit)("bodyCalls", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("c"))]),
|
|
975
|
+
(0, import_datalog3.rule)(
|
|
874
976
|
"bodyCallsDeep",
|
|
875
|
-
[(0,
|
|
876
|
-
[(0,
|
|
977
|
+
[(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("c")],
|
|
978
|
+
[(0, import_datalog3.lit)("containsFn", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("g")), (0, import_datalog3.lit)("bodyCallsDeep", (0, import_datalog3.variable)("g"), (0, import_datalog3.variable)("c"))]
|
|
877
979
|
),
|
|
878
|
-
(0,
|
|
980
|
+
(0, import_datalog3.rule)(
|
|
879
981
|
"unwraps",
|
|
880
|
-
[(0,
|
|
982
|
+
[(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k")],
|
|
881
983
|
[
|
|
882
|
-
(0,
|
|
883
|
-
(0,
|
|
884
|
-
(0,
|
|
885
|
-
(0,
|
|
984
|
+
(0, import_datalog3.lit)("returnsFunc", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("g")),
|
|
985
|
+
(0, import_datalog3.lit)("bodyCallsDeep", (0, import_datalog3.variable)("g"), (0, import_datalog3.variable)("c")),
|
|
986
|
+
(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("p")),
|
|
987
|
+
(0, import_datalog3.lit)("paramOf", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("p"))
|
|
886
988
|
]
|
|
887
989
|
),
|
|
888
990
|
// Argument flow: which parameter a value traces back to. Directly
|
|
@@ -890,304 +992,289 @@ var RESOLUTION_RULES = [
|
|
|
890
992
|
// another unwrapping factory. This is what lets
|
|
891
993
|
// `createProtected(h) { return service.withAuth(h); }` unwrap:
|
|
892
994
|
// the returned call passes h through withAuth, which unwraps.
|
|
893
|
-
(0,
|
|
995
|
+
(0, import_datalog3.rule)(
|
|
894
996
|
"flowsToParam",
|
|
895
|
-
[(0,
|
|
997
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("p")],
|
|
896
998
|
[
|
|
897
|
-
(0,
|
|
898
|
-
(0,
|
|
999
|
+
(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("p")),
|
|
1000
|
+
(0, import_datalog3.lit)("paramOf", (0, import_datalog3.variable)("anyF"), (0, import_datalog3.variable)("anyK"), (0, import_datalog3.variable)("p"))
|
|
899
1001
|
]
|
|
900
1002
|
),
|
|
901
|
-
(0,
|
|
1003
|
+
(0, import_datalog3.rule)(
|
|
902
1004
|
"flowsToParam",
|
|
903
|
-
[(0,
|
|
1005
|
+
[(0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p")],
|
|
904
1006
|
[
|
|
905
|
-
(0,
|
|
906
|
-
(0,
|
|
907
|
-
(0,
|
|
908
|
-
(0,
|
|
909
|
-
(0,
|
|
1007
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c")),
|
|
1008
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f")),
|
|
1009
|
+
(0, import_datalog3.lit)("unwraps", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k")),
|
|
1010
|
+
(0, import_datalog3.lit)("callArg", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("a")),
|
|
1011
|
+
(0, import_datalog3.lit)("flowsToParam", (0, import_datalog3.variable)("a"), (0, import_datalog3.variable)("p"))
|
|
910
1012
|
]
|
|
911
1013
|
),
|
|
912
|
-
(0,
|
|
1014
|
+
(0, import_datalog3.rule)(
|
|
913
1015
|
"unwraps",
|
|
914
|
-
[(0,
|
|
1016
|
+
[(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k")],
|
|
915
1017
|
[
|
|
916
|
-
(0,
|
|
917
|
-
(0,
|
|
918
|
-
(0,
|
|
1018
|
+
(0, import_datalog3.lit)("returnsValue", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("value")),
|
|
1019
|
+
(0, import_datalog3.lit)("flowsToParam", (0, import_datalog3.variable)("value"), (0, import_datalog3.variable)("p")),
|
|
1020
|
+
(0, import_datalog3.lit)("paramOf", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("k"), (0, import_datalog3.variable)("p"))
|
|
919
1021
|
]
|
|
920
1022
|
),
|
|
921
1023
|
// Where a name comes from, when what it refers to lives outside the
|
|
922
1024
|
// source being read. A walk ends at something written out in source,
|
|
923
1025
|
// so it never reaches a library's own function.
|
|
924
|
-
(0,
|
|
1026
|
+
(0, import_datalog3.rule)(
|
|
925
1027
|
"comesFrom",
|
|
926
|
-
[(0,
|
|
927
|
-
[(0,
|
|
1028
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
1029
|
+
[(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))]
|
|
928
1030
|
),
|
|
929
|
-
(0,
|
|
1031
|
+
(0, import_datalog3.rule)(
|
|
930
1032
|
"comesFrom",
|
|
931
|
-
[(0,
|
|
1033
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
932
1034
|
[
|
|
933
|
-
(0,
|
|
934
|
-
(0,
|
|
1035
|
+
(0, import_datalog3.lit)("reaches", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), VALUE_STEP),
|
|
1036
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
935
1037
|
]
|
|
936
1038
|
),
|
|
937
1039
|
// Calling f ends up calling the name n that module m exports, one
|
|
938
1040
|
// hop through f's own body or deeper through a wrapper of a wrapper.
|
|
939
1041
|
// Several results is normal: a composed decorator applies them all.
|
|
940
|
-
(0,
|
|
1042
|
+
(0, import_datalog3.rule)(
|
|
941
1043
|
"callsInto",
|
|
942
|
-
[(0,
|
|
1044
|
+
[(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
943
1045
|
[
|
|
944
|
-
(0,
|
|
945
|
-
(0,
|
|
1046
|
+
(0, import_datalog3.lit)("bodyCallsDeep", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("c")),
|
|
1047
|
+
(0, import_datalog3.lit)("comesFrom", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
946
1048
|
]
|
|
947
1049
|
),
|
|
948
|
-
(0,
|
|
1050
|
+
(0, import_datalog3.rule)(
|
|
949
1051
|
"callsInto",
|
|
950
|
-
[(0,
|
|
1052
|
+
[(0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
951
1053
|
[
|
|
952
|
-
(0,
|
|
953
|
-
(0,
|
|
954
|
-
(0,
|
|
1054
|
+
(0, import_datalog3.lit)("bodyCallsDeep", (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("c")),
|
|
1055
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("g")),
|
|
1056
|
+
(0, import_datalog3.lit)("callsInto", (0, import_datalog3.variable)("g"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
955
1057
|
]
|
|
956
1058
|
),
|
|
957
1059
|
// The question callers ask: what a value comes to, narrowed to the
|
|
958
1060
|
// functions. Objects appear in the middle of chains and never in an
|
|
959
1061
|
// answer.
|
|
960
|
-
(0,
|
|
1062
|
+
(0, import_datalog3.rule)(
|
|
961
1063
|
"resolves",
|
|
962
|
-
[(0,
|
|
963
|
-
[(0,
|
|
1064
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1065
|
+
[(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")), (0, import_datalog3.lit)("func", (0, import_datalog3.variable)("z"))]
|
|
964
1066
|
)
|
|
965
1067
|
];
|
|
966
1068
|
var RESOLUTION_QUESTIONS = [
|
|
967
|
-
(0,
|
|
1069
|
+
(0, import_datalog3.rule)(
|
|
968
1070
|
"wantedResolves",
|
|
969
|
-
[(0,
|
|
970
|
-
[(0,
|
|
1071
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1072
|
+
[(0, import_datalog3.lit)("wanted", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("resolves", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"))]
|
|
971
1073
|
),
|
|
972
|
-
(0,
|
|
1074
|
+
(0, import_datalog3.rule)(
|
|
973
1075
|
"wantedComesTo",
|
|
974
|
-
[(0,
|
|
975
|
-
[(0,
|
|
1076
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1077
|
+
[(0, import_datalog3.lit)("wanted", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"))]
|
|
976
1078
|
),
|
|
977
|
-
(0,
|
|
1079
|
+
(0, import_datalog3.rule)(
|
|
978
1080
|
"wantedComesTo",
|
|
979
|
-
[(0,
|
|
980
|
-
[(0,
|
|
1081
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1082
|
+
[(0, import_datalog3.lit)("wantedOrigin", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"))]
|
|
981
1083
|
),
|
|
982
|
-
(0,
|
|
1084
|
+
(0, import_datalog3.rule)(
|
|
983
1085
|
"wantedIsWrittenAs",
|
|
984
|
-
[(0,
|
|
985
|
-
[(0,
|
|
1086
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1087
|
+
[(0, import_datalog3.lit)("wanted", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("isWrittenAs", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"))]
|
|
986
1088
|
),
|
|
987
1089
|
// A call is given no `comesTo`, so this is the only way to ask what
|
|
988
1090
|
// object one arrives at, and without it a demand-driven run derives
|
|
989
1091
|
// `objectOf` nowhere.
|
|
990
|
-
(0,
|
|
1092
|
+
(0, import_datalog3.rule)(
|
|
991
1093
|
"wantedObjectOf",
|
|
992
|
-
[(0,
|
|
993
|
-
[(0,
|
|
1094
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1095
|
+
[(0, import_datalog3.lit)("wanted", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("objectOf", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"))]
|
|
994
1096
|
),
|
|
995
1097
|
// Keyed by the parameter, since that is what a caller has in hand
|
|
996
1098
|
// when it wants the call sites told apart.
|
|
997
|
-
(0,
|
|
1099
|
+
(0, import_datalog3.rule)(
|
|
998
1100
|
"wantedParamAt",
|
|
999
|
-
[(0,
|
|
1000
|
-
[(0,
|
|
1101
|
+
[(0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("z")],
|
|
1102
|
+
[(0, import_datalog3.lit)("wanted", (0, import_datalog3.variable)("p")), (0, import_datalog3.lit)("paramAt", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("p"), (0, import_datalog3.variable)("z"))]
|
|
1001
1103
|
),
|
|
1002
|
-
(0,
|
|
1104
|
+
(0, import_datalog3.rule)(
|
|
1003
1105
|
"wantedComesFrom",
|
|
1004
|
-
[(0,
|
|
1005
|
-
[(0,
|
|
1106
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
1107
|
+
[(0, import_datalog3.lit)("wantedOrigin", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("comesFrom", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))]
|
|
1006
1108
|
),
|
|
1007
1109
|
// Call-origin questions, for attribution, in their own demand
|
|
1008
1110
|
// class. Attribution stops at the import declaration, so nothing
|
|
1009
1111
|
// here demands reaches or callsInto. The chains are closures with
|
|
1010
1112
|
// no depth bound: an alias run of any length resolves.
|
|
1011
|
-
(0,
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1016
|
-
),
|
|
1017
|
-
(0, import_datalog2.rule)(
|
|
1018
|
-
"callOriginChain",
|
|
1019
|
-
[(0, import_datalog2.variable)("x"), (0, import_datalog2.variable)("z")],
|
|
1020
|
-
[
|
|
1021
|
-
(0, import_datalog2.lit)("callOriginChain", (0, import_datalog2.variable)("x"), (0, import_datalog2.variable)("y")),
|
|
1022
|
-
(0, import_datalog2.lit)("endsHolding", (0, import_datalog2.variable)("y"), (0, import_datalog2.variable)("z"))
|
|
1023
|
-
]
|
|
1024
|
-
),
|
|
1025
|
-
(0, import_datalog2.rule)(
|
|
1113
|
+
(0, import_datalog3.rule)("callOriginChain", [(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("x")], [(0, import_datalog3.lit)("wantedCallOrigin", (0, import_datalog3.variable)("x"))]),
|
|
1114
|
+
// The chain with at least one hop taken, which is what tells a
|
|
1115
|
+
// destructured binding apart from asking about a node directly. The
|
|
1116
|
+
// whole chain is the seed plus those hops.
|
|
1117
|
+
(0, import_datalog3.rule)(
|
|
1026
1118
|
"callOriginChain",
|
|
1027
|
-
[(0,
|
|
1028
|
-
[
|
|
1029
|
-
(0, import_datalog2.lit)("callOriginChain", (0, import_datalog2.variable)("x"), (0, import_datalog2.variable)("y")),
|
|
1030
|
-
(0, import_datalog2.lit)("fallbackBranch", (0, import_datalog2.variable)("y"), (0, import_datalog2.variable)("z"))
|
|
1031
|
-
]
|
|
1119
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1120
|
+
[(0, import_datalog3.lit)("callOriginChainStepped", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"))]
|
|
1032
1121
|
),
|
|
1033
|
-
|
|
1034
|
-
// destructured binding apart from asking about a node directly.
|
|
1035
|
-
(0, import_datalog2.rule)(
|
|
1122
|
+
(0, import_datalog3.rule)(
|
|
1036
1123
|
"callOriginChainStepped",
|
|
1037
|
-
[(0,
|
|
1038
|
-
[(0,
|
|
1124
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1125
|
+
[(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")), (0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))]
|
|
1039
1126
|
),
|
|
1040
|
-
(0,
|
|
1127
|
+
(0, import_datalog3.rule)(
|
|
1041
1128
|
"callOriginChainStepped",
|
|
1042
|
-
[(0,
|
|
1129
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1043
1130
|
[
|
|
1044
|
-
(0,
|
|
1045
|
-
(0,
|
|
1131
|
+
(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1132
|
+
(0, import_datalog3.lit)("endsHolding", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))
|
|
1046
1133
|
]
|
|
1047
1134
|
),
|
|
1048
|
-
(0,
|
|
1135
|
+
(0, import_datalog3.rule)(
|
|
1049
1136
|
"callOriginChainStepped",
|
|
1050
|
-
[(0,
|
|
1137
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1051
1138
|
[
|
|
1052
|
-
(0,
|
|
1053
|
-
(0,
|
|
1139
|
+
(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1140
|
+
(0, import_datalog3.lit)("fallbackBranch", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))
|
|
1054
1141
|
]
|
|
1055
1142
|
),
|
|
1056
|
-
(0,
|
|
1143
|
+
(0, import_datalog3.rule)(
|
|
1057
1144
|
"wantedCallOriginPair",
|
|
1058
|
-
[(0,
|
|
1145
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
1059
1146
|
[
|
|
1060
|
-
(0,
|
|
1061
|
-
(0,
|
|
1147
|
+
(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1148
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
1062
1149
|
]
|
|
1063
1150
|
),
|
|
1064
1151
|
// An import of a project barrel is an import of what the barrel
|
|
1065
1152
|
// forwards, so the pair surfaces the module behind the chain.
|
|
1066
|
-
(0,
|
|
1153
|
+
(0, import_datalog3.rule)(
|
|
1067
1154
|
"wantedCallOriginPair",
|
|
1068
|
-
[(0,
|
|
1155
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2")],
|
|
1069
1156
|
[
|
|
1070
|
-
(0,
|
|
1071
|
-
(0,
|
|
1072
|
-
(0,
|
|
1157
|
+
(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1158
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")),
|
|
1159
|
+
(0, import_datalog3.lit)("moduleForwards", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("m2"), (0, import_datalog3.variable)("n2"))
|
|
1073
1160
|
]
|
|
1074
1161
|
),
|
|
1075
1162
|
// A namespace member: the module's export of the member's own name.
|
|
1076
1163
|
// The imports literal leads, since it is the smallest relation.
|
|
1077
|
-
(0,
|
|
1164
|
+
(0, import_datalog3.rule)(
|
|
1078
1165
|
"wantedCallOriginPair",
|
|
1079
|
-
[(0,
|
|
1166
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("p")],
|
|
1080
1167
|
[
|
|
1081
|
-
(0,
|
|
1082
|
-
(0,
|
|
1083
|
-
(0,
|
|
1168
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("m"), NAMESPACE_IMPORT),
|
|
1169
|
+
(0, import_datalog3.lit)("readsProperty", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("p")),
|
|
1170
|
+
(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"))
|
|
1084
1171
|
]
|
|
1085
1172
|
),
|
|
1086
|
-
(0,
|
|
1173
|
+
(0, import_datalog3.rule)(
|
|
1087
1174
|
"wantedCallOriginPair",
|
|
1088
|
-
[(0,
|
|
1175
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("p")],
|
|
1089
1176
|
[
|
|
1090
|
-
(0,
|
|
1091
|
-
(0,
|
|
1092
|
-
(0,
|
|
1093
|
-
(0,
|
|
1177
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("d"), (0, import_datalog3.variable)("m"), NAMESPACE_IMPORT),
|
|
1178
|
+
(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("d")),
|
|
1179
|
+
(0, import_datalog3.lit)("readsProperty", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("p")),
|
|
1180
|
+
(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"))
|
|
1094
1181
|
]
|
|
1095
1182
|
),
|
|
1096
1183
|
// What a call made: through the call to its callee, whose own alias
|
|
1097
1184
|
// chain leads to the import.
|
|
1098
|
-
(0,
|
|
1185
|
+
(0, import_datalog3.rule)(
|
|
1099
1186
|
"callMadeChain",
|
|
1100
|
-
[(0,
|
|
1101
|
-
[(0,
|
|
1187
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("f")],
|
|
1188
|
+
[(0, import_datalog3.lit)("callOriginChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("c")), (0, import_datalog3.lit)("call", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f"))]
|
|
1102
1189
|
),
|
|
1103
|
-
(0,
|
|
1190
|
+
(0, import_datalog3.rule)(
|
|
1104
1191
|
"callMadeChain",
|
|
1105
|
-
[(0,
|
|
1106
|
-
[(0,
|
|
1192
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1193
|
+
[(0, import_datalog3.lit)("callMadeChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")), (0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))]
|
|
1107
1194
|
),
|
|
1108
|
-
(0,
|
|
1195
|
+
(0, import_datalog3.rule)(
|
|
1109
1196
|
"callMadeChain",
|
|
1110
|
-
[(0,
|
|
1111
|
-
[(0,
|
|
1197
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1198
|
+
[(0, import_datalog3.lit)("callMadeChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")), (0, import_datalog3.lit)("endsHolding", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))]
|
|
1112
1199
|
),
|
|
1113
|
-
(0,
|
|
1200
|
+
(0, import_datalog3.rule)(
|
|
1114
1201
|
"wantedCallOriginPair",
|
|
1115
|
-
[(0,
|
|
1202
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
1116
1203
|
[
|
|
1117
|
-
(0,
|
|
1118
|
-
(0,
|
|
1204
|
+
(0, import_datalog3.lit)("callMadeChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1205
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
1119
1206
|
]
|
|
1120
1207
|
),
|
|
1121
1208
|
// A member destructured off what a call made keeps the member name
|
|
1122
1209
|
// as one more path segment.
|
|
1123
|
-
(0,
|
|
1210
|
+
(0, import_datalog3.rule)(
|
|
1124
1211
|
"callMemberChain",
|
|
1125
|
-
[(0,
|
|
1212
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("f"), (0, import_datalog3.variable)("p")],
|
|
1126
1213
|
[
|
|
1127
|
-
(0,
|
|
1128
|
-
(0,
|
|
1129
|
-
(0,
|
|
1214
|
+
(0, import_datalog3.lit)("callOriginChainStepped", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("e")),
|
|
1215
|
+
(0, import_datalog3.lit)("readsProperty", (0, import_datalog3.variable)("e"), (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("p")),
|
|
1216
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("f"))
|
|
1130
1217
|
]
|
|
1131
1218
|
),
|
|
1132
|
-
(0,
|
|
1219
|
+
(0, import_datalog3.rule)(
|
|
1133
1220
|
"callMemberChain",
|
|
1134
|
-
[(0,
|
|
1221
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), (0, import_datalog3.variable)("p")],
|
|
1135
1222
|
[
|
|
1136
|
-
(0,
|
|
1137
|
-
(0,
|
|
1223
|
+
(0, import_datalog3.lit)("callMemberChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("p")),
|
|
1224
|
+
(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))
|
|
1138
1225
|
]
|
|
1139
1226
|
),
|
|
1140
|
-
(0,
|
|
1227
|
+
(0, import_datalog3.rule)(
|
|
1141
1228
|
"callMemberChain",
|
|
1142
|
-
[(0,
|
|
1229
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z"), (0, import_datalog3.variable)("p")],
|
|
1143
1230
|
[
|
|
1144
|
-
(0,
|
|
1145
|
-
(0,
|
|
1231
|
+
(0, import_datalog3.lit)("callMemberChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("p")),
|
|
1232
|
+
(0, import_datalog3.lit)("endsHolding", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))
|
|
1146
1233
|
]
|
|
1147
1234
|
),
|
|
1148
|
-
(0,
|
|
1235
|
+
(0, import_datalog3.rule)(
|
|
1149
1236
|
"wantedCallOriginMember",
|
|
1150
|
-
[(0,
|
|
1237
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("p")],
|
|
1151
1238
|
[
|
|
1152
|
-
(0,
|
|
1153
|
-
(0,
|
|
1239
|
+
(0, import_datalog3.lit)("callMemberChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("p")),
|
|
1240
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
1154
1241
|
]
|
|
1155
1242
|
),
|
|
1156
|
-
(0,
|
|
1243
|
+
(0, import_datalog3.rule)(
|
|
1157
1244
|
"wantedCallsInto",
|
|
1158
|
-
[(0,
|
|
1245
|
+
[(0, import_datalog3.variable)("g"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
1159
1246
|
[
|
|
1160
|
-
(0,
|
|
1161
|
-
(0,
|
|
1162
|
-
(0,
|
|
1247
|
+
(0, import_datalog3.lit)("wantedOrigin", (0, import_datalog3.variable)("x")),
|
|
1248
|
+
(0, import_datalog3.lit)("comesTo", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("g")),
|
|
1249
|
+
(0, import_datalog3.lit)("callsInto", (0, import_datalog3.variable)("g"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
1163
1250
|
]
|
|
1164
1251
|
),
|
|
1165
1252
|
// Subject identity, its own demand class; the README's subject
|
|
1166
1253
|
// section says why the origin pair rides on the written-value walk.
|
|
1167
|
-
(0,
|
|
1254
|
+
(0, import_datalog3.rule)(
|
|
1168
1255
|
"wantedSubjectWritten",
|
|
1169
|
-
[(0,
|
|
1170
|
-
[(0,
|
|
1256
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r")],
|
|
1257
|
+
[(0, import_datalog3.lit)("wantedSubject", (0, import_datalog3.variable)("x")), (0, import_datalog3.lit)("isWrittenAs", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r"))]
|
|
1171
1258
|
),
|
|
1172
|
-
(0,
|
|
1259
|
+
(0, import_datalog3.rule)(
|
|
1173
1260
|
"wantedSubjectConstruction",
|
|
1174
|
-
[(0,
|
|
1261
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")],
|
|
1175
1262
|
[
|
|
1176
|
-
(0,
|
|
1177
|
-
(0,
|
|
1178
|
-
(0,
|
|
1179
|
-
(0,
|
|
1263
|
+
(0, import_datalog3.lit)("wantedSubject", (0, import_datalog3.variable)("x")),
|
|
1264
|
+
(0, import_datalog3.lit)("isWrittenAs", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r")),
|
|
1265
|
+
(0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c")),
|
|
1266
|
+
(0, import_datalog3.lit)("comesFrom", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"))
|
|
1180
1267
|
]
|
|
1181
1268
|
),
|
|
1182
1269
|
// The export table of one module, keyed by the module asked about.
|
|
1183
1270
|
// The moduleExport rules flatten re-export chains of any length, and
|
|
1184
1271
|
// the demand cone stays on export facts alone.
|
|
1185
|
-
(0,
|
|
1272
|
+
(0, import_datalog3.rule)(
|
|
1186
1273
|
"wantedModuleExport",
|
|
1187
|
-
[(0,
|
|
1274
|
+
[(0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value")],
|
|
1188
1275
|
[
|
|
1189
|
-
(0,
|
|
1190
|
-
(0,
|
|
1276
|
+
(0, import_datalog3.lit)("wantedExportsOf", (0, import_datalog3.variable)("m")),
|
|
1277
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("value"))
|
|
1191
1278
|
]
|
|
1192
1279
|
),
|
|
1193
1280
|
// The calls behind a receiver, for a pack that wants the anchor a
|
|
@@ -1196,63 +1283,63 @@ var RESOLUTION_QUESTIONS = [
|
|
|
1196
1283
|
// A class's ancestry, one hop per extends through the binding that
|
|
1197
1284
|
// says which class the written base is; the names on the way out
|
|
1198
1285
|
// are what a storage pack matches its library's bases against.
|
|
1199
|
-
(0,
|
|
1200
|
-
(0,
|
|
1286
|
+
(0, import_datalog3.rule)("ancestryChain", [(0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("c")], [(0, import_datalog3.lit)("wantedAncestry", (0, import_datalog3.variable)("c"))]),
|
|
1287
|
+
(0, import_datalog3.rule)(
|
|
1201
1288
|
"ancestryChain",
|
|
1202
|
-
[(0,
|
|
1289
|
+
[(0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("b2")],
|
|
1203
1290
|
[
|
|
1204
|
-
(0,
|
|
1205
|
-
(0,
|
|
1206
|
-
(0,
|
|
1291
|
+
(0, import_datalog3.lit)("ancestryChain", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("b")),
|
|
1292
|
+
(0, import_datalog3.lit)("extends", (0, import_datalog3.variable)("b"), (0, import_datalog3.variable)("x")),
|
|
1293
|
+
(0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("b2"))
|
|
1207
1294
|
]
|
|
1208
1295
|
),
|
|
1209
|
-
(0,
|
|
1296
|
+
(0, import_datalog3.rule)(
|
|
1210
1297
|
"wantedBaseName",
|
|
1211
|
-
[(0,
|
|
1212
|
-
[(0,
|
|
1298
|
+
[(0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("n")],
|
|
1299
|
+
[(0, import_datalog3.lit)("ancestryChain", (0, import_datalog3.variable)("c"), (0, import_datalog3.variable)("b")), (0, import_datalog3.lit)("extendsNamed", (0, import_datalog3.variable)("b"), (0, import_datalog3.variable)("n"))]
|
|
1213
1300
|
),
|
|
1214
|
-
(0,
|
|
1215
|
-
(0,
|
|
1301
|
+
(0, import_datalog3.rule)("anchorChain", [(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("x")], [(0, import_datalog3.lit)("wantedAnchor", (0, import_datalog3.variable)("x"))]),
|
|
1302
|
+
(0, import_datalog3.rule)(
|
|
1216
1303
|
"anchorChain",
|
|
1217
|
-
[(0,
|
|
1218
|
-
[(0,
|
|
1304
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1305
|
+
[(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")), (0, import_datalog3.lit)("binds", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))]
|
|
1219
1306
|
),
|
|
1220
|
-
(0,
|
|
1307
|
+
(0, import_datalog3.rule)(
|
|
1221
1308
|
"anchorChain",
|
|
1222
|
-
[(0,
|
|
1223
|
-
[(0,
|
|
1309
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1310
|
+
[(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")), (0, import_datalog3.lit)("endsHolding", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))]
|
|
1224
1311
|
),
|
|
1225
|
-
(0,
|
|
1312
|
+
(0, import_datalog3.rule)(
|
|
1226
1313
|
"anchorChain",
|
|
1227
|
-
[(0,
|
|
1228
|
-
[(0,
|
|
1314
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1315
|
+
[(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")), (0, import_datalog3.lit)("fallbackBranch", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("z"))]
|
|
1229
1316
|
),
|
|
1230
|
-
(0,
|
|
1317
|
+
(0, import_datalog3.rule)(
|
|
1231
1318
|
"anchorChain",
|
|
1232
|
-
[(0,
|
|
1319
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("z")],
|
|
1233
1320
|
[
|
|
1234
|
-
(0,
|
|
1235
|
-
(0,
|
|
1236
|
-
(0,
|
|
1321
|
+
(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1322
|
+
(0, import_datalog3.lit)("imports", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n")),
|
|
1323
|
+
(0, import_datalog3.lit)("moduleExport", (0, import_datalog3.variable)("m"), (0, import_datalog3.variable)("n"), (0, import_datalog3.variable)("z"))
|
|
1237
1324
|
]
|
|
1238
1325
|
),
|
|
1239
|
-
(0,
|
|
1326
|
+
(0, import_datalog3.rule)(
|
|
1240
1327
|
"anchorChain",
|
|
1241
|
-
[(0,
|
|
1242
|
-
[(0,
|
|
1328
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("c")],
|
|
1329
|
+
[(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r")), (0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c"))]
|
|
1243
1330
|
),
|
|
1244
|
-
(0,
|
|
1331
|
+
(0, import_datalog3.rule)(
|
|
1245
1332
|
"anchorChain",
|
|
1246
|
-
[(0,
|
|
1333
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("o")],
|
|
1247
1334
|
[
|
|
1248
|
-
(0,
|
|
1249
|
-
(0,
|
|
1335
|
+
(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("y")),
|
|
1336
|
+
(0, import_datalog3.lit)("readsProperty", (0, import_datalog3.variable)("y"), (0, import_datalog3.variable)("o"), (0, import_datalog3.variable)("n"))
|
|
1250
1337
|
]
|
|
1251
1338
|
),
|
|
1252
|
-
(0,
|
|
1339
|
+
(0, import_datalog3.rule)(
|
|
1253
1340
|
"wantedAnchorCall",
|
|
1254
|
-
[(0,
|
|
1255
|
-
[(0,
|
|
1341
|
+
[(0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r")],
|
|
1342
|
+
[(0, import_datalog3.lit)("anchorChain", (0, import_datalog3.variable)("x"), (0, import_datalog3.variable)("r")), (0, import_datalog3.lit)("call", (0, import_datalog3.variable)("r"), (0, import_datalog3.variable)("c"))]
|
|
1256
1343
|
)
|
|
1257
1344
|
];
|
|
1258
1345
|
var ANSWER_RELATIONS = [
|
|
@@ -1271,7 +1358,10 @@ var ANSWER_RELATIONS = [
|
|
|
1271
1358
|
agreedMountPrefix,
|
|
1272
1359
|
checkFactContract,
|
|
1273
1360
|
explainResolutionProof,
|
|
1361
|
+
explainResolvedKey,
|
|
1274
1362
|
joinMountedPath,
|
|
1275
1363
|
mountPathsOf,
|
|
1276
|
-
|
|
1364
|
+
placeholderValues,
|
|
1365
|
+
renderExplanation,
|
|
1366
|
+
singleAnswers
|
|
1277
1367
|
});
|