@@ -37,9 +37,41 @@ RewriteSystem::~RewriteSystem() {
37
37
Context.RuleTrieRootHistogram );
38
38
}
39
39
40
+ // / Initialize the rewrite system using rewrite rules built by the RuleBuilder.
41
+ // /
42
+ // / - recordLoops: Whether this is a rewrite system built from user-written
43
+ // / requirements, in which case we will perform minimization using rewrite
44
+ // / loops recorded during completion.
45
+ // /
46
+ // / - protos: If this is a rewrite system built from a protocol connected
47
+ // / component, this contains the members of the protocol. For a rewrite
48
+ // / system built from a generic signature, this is empty. Used by
49
+ // / RewriteSystem::isInMinimizationDomain().
50
+ // /
51
+ // / These parameters should be populated from the corresponding fields of the
52
+ // / RuleBuilder instance:
53
+ // /
54
+ // / - writtenRequirements: The user-written requirements, if any, used to
55
+ // / track source locations for redundancy diagnostics.
56
+ // /
57
+ // / - importedRules: Rewrite rules for referenced protocols. These come from
58
+ // / the Requirement Machine instances for these protocols' connected
59
+ // / components, so they are already confluent and can be imported verbatim.
60
+ // /
61
+ // / - permanentRules: Permanent rules, such as associated type introduction
62
+ // / rules for associated types defined in protocols in this connected
63
+ // / component.
64
+ // /
65
+ // / - requirementRules: Rules corresponding to generic requirements written
66
+ // / by the user.
67
+ // /
68
+ // / This can only be called once. It adds the rules to the rewrite system,
69
+ // / allowing computeConfluentCompletion() to be called to compute the
70
+ // / complete rewrite system.
40
71
void RewriteSystem::initialize (
41
72
bool recordLoops, ArrayRef<const ProtocolDecl *> protos,
42
73
ArrayRef<StructuralRequirement> writtenRequirements,
74
+ std::vector<Rule> &&importedRules,
43
75
std::vector<std::pair<MutableTerm, MutableTerm>> &&permanentRules,
44
76
std::vector<std::tuple<MutableTerm, MutableTerm, Optional<unsigned >>>
45
77
&&requirementRules) {
@@ -50,6 +82,36 @@ void RewriteSystem::initialize(
50
82
Protos = protos;
51
83
WrittenRequirements = writtenRequirements;
52
84
85
+ // Pre-populate our rules vector with the list of imported rules, and note
86
+ // the position of the first local (not imported) rule.
87
+ Rules = std::move (importedRules);
88
+ FirstLocalRule = Rules.size ();
89
+
90
+ // Add the imported rules to the trie.
91
+ for (unsigned newRuleID : indices (Rules)) {
92
+ const auto &newRule = Rules[newRuleID];
93
+ // Skip simplified rules. At the very least we need to skip RHS-simplified
94
+ // rules since their left hand sides might duplicate existing rules; the
95
+ // others are skipped purely as an optimization.
96
+ if (newRule.isLHSSimplified () ||
97
+ newRule.isRHSSimplified () ||
98
+ newRule.isSubstitutionSimplified ())
99
+ continue ;
100
+
101
+ auto oldRuleID = Trie.insert (newRule.getLHS ().begin (),
102
+ newRule.getLHS ().end (),
103
+ newRuleID);
104
+ if (oldRuleID) {
105
+ llvm::errs () << " Imported rules have duplicate left hand sides!\n " ;
106
+ llvm::errs () << " New rule #" << newRuleID << " : " << newRule << " \n " ;
107
+ const auto &oldRule = getRule (*oldRuleID);
108
+ llvm::errs () << " Old rule #" << *oldRuleID << " : " << oldRule << " \n\n " ;
109
+ dump (llvm::errs ());
110
+ abort ();
111
+ }
112
+ }
113
+
114
+ // Now add our own rules.
53
115
for (const auto &rule : permanentRules)
54
116
addPermanentRule (rule.first , rule.second );
55
117
0 commit comments