1 /*
2
3 This file is part of the Maude 2 interpreter.
4
5 Copyright 1997-2003 SRI International, Menlo Park, CA 94025, USA.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
20
21 */
22
23 //
24 // Class to hold variable information passed down through
25 // compilation functions.
26 //
27 #ifndef _variableInfo_hh_
28 #define _variableInfo_hh_
29 #include "natSet.hh"
30 #include "variableTerm.hh"
31
32 class VariableInfo
33 {
34 public:
35 VariableInfo();
36
37 int getNrRealVariables() const;
38 int getNrProtectedVariables() const;
39 //
40 // These two functions map between indexes and real variables.
41 //
42 int variable2Index(VariableTerm* variableTerm);
43 Term* index2Variable(int index) const;
44 //
45 // The following function makes a new variable which will be
46 // (1) Cleared before matching;
47 // (2) Copied when a copy of substitution is made;
48 // (3) Considered for local binding in a given branch of matching; and
49 // (4) Protected from garbage collection.
50 //
51 int makeProtectedVariable();
52 //
53 // Construction indexes are initially >= MAX_NR_PROTECTED_VARIABLES.
54 // A construction index that is reused across two or more different
55 // fragments must be remapped to a protected variable.
56 // Others construction indices will be remapped to the indices at the
57 // end of the substitution and these indices can be reused for different
58 // things in different fragments since they are not protected in any way.
59 //
60 int makeConstructionIndex();
61 void endOfFragment();
62 void useIndex(int index);
63 int computeIndexRemapping();
64 int remapIndex(int original);
65 //
66 // Separate from the above we keep sets (of indices) of real variables
67 // at occur in the condition or are used before being bound.
68 //
69 void addConditionVariables(const NatSet& vars);
70 void addUnboundVariables(const NatSet& vars);
71 const NatSet& getConditionVariables() const;
72 const NatSet& getUnboundVariables() const;
73
74 //
75 // Decide if an index is read or virtual.
76 //
77 static bool isReal(int index);
78
79 private:
80 enum Values
81 {
82 MAX_NR_PROTECTED_VARIABLES = 10000000
83 };
84
85 struct ConstructionIndex
86 {
87 int lastUseTime; // number of construction indices allocated at last use
88 short assignedFragment;
89 short lastUseFragment;
90 int newIndex;
91 };
92
93 Vector<Term*> variables;
94 int nrProtectedVariables;
95 int fragmentNumber;
96 Vector<ConstructionIndex> constructionIndices;
97 NatSet conditionVariables;
98 NatSet unboundVariables;
99 };
100
101 inline int
getNrRealVariables() const102 VariableInfo::getNrRealVariables() const
103 {
104 return variables.length();
105 }
106
107 inline int
getNrProtectedVariables() const108 VariableInfo::getNrProtectedVariables() const
109 {
110 return nrProtectedVariables;
111 }
112
113 inline Term*
index2Variable(int index) const114 VariableInfo::index2Variable(int index) const
115 {
116 return variables[index];
117 }
118
119 inline int
makeProtectedVariable()120 VariableInfo::makeProtectedVariable()
121 {
122 return nrProtectedVariables++;
123 }
124
125 inline void
endOfFragment()126 VariableInfo::endOfFragment()
127 {
128 ++fragmentNumber;
129 }
130
131 inline int
remapIndex(int original)132 VariableInfo::remapIndex(int original)
133 {
134 if (original >= MAX_NR_PROTECTED_VARIABLES)
135 return constructionIndices[original - MAX_NR_PROTECTED_VARIABLES].newIndex;
136 return original;
137 }
138
139 inline void
useIndex(int index)140 VariableInfo::useIndex(int index)
141 {
142 if (index >= MAX_NR_PROTECTED_VARIABLES)
143 {
144 index -= MAX_NR_PROTECTED_VARIABLES;
145 constructionIndices[index].lastUseTime = constructionIndices.length();
146 constructionIndices[index].lastUseFragment = fragmentNumber;
147 }
148 }
149
150 inline const NatSet&
getConditionVariables() const151 VariableInfo::getConditionVariables() const
152 {
153 return conditionVariables;
154 }
155
156 inline const NatSet&
getUnboundVariables() const157 VariableInfo::getUnboundVariables() const
158 {
159 return unboundVariables;
160 }
161
162 inline void
addConditionVariables(const NatSet & vars)163 VariableInfo::addConditionVariables(const NatSet& vars)
164 {
165 conditionVariables.insert(vars);
166 }
167
168 inline void
addUnboundVariables(const NatSet & vars)169 VariableInfo::addUnboundVariables(const NatSet& vars)
170 {
171 unboundVariables.insert(vars);
172 }
173
174 inline bool
isReal(int index)175 VariableInfo::isReal(int index)
176 {
177 return index < MAX_NR_PROTECTED_VARIABLES;
178 }
179
180 #endif
181