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 ImportModule*
makeRenamedCopy(int name,Renaming * canonical,ModuleCache * moduleCache)24 ImportModule::makeRenamedCopy(int name, Renaming* canonical, ModuleCache* moduleCache)
25 {
26 ImportModule* copy = new ImportModule(name, getModuleType(), RENAMING, moduleCache);
27 DebugAdvisory("makeRenamedCopy() made " << copy << " at address " << static_cast<void*>(copy));
28 LineNumber lineNumber(FileTable::AUTOMATIC);
29
30 int nrParameters = parameterNames.size();
31 for (int i = 0; i < nrParameters; ++i)
32 {
33 Token t;
34 t.tokenize(parameterNames[i], FileTable::AUTOMATIC);
35 copy->addParameter(t, importedModules[i]);
36 }
37 //Assert(!parametersBound(), "renamed module has bound parameters");
38
39 int nrImports = importedModules.size();
40 for (int i = nrParameters; i < nrImports; ++i)
41 {
42 if (ImportModule* importCopy = moduleCache->makeRenamedCopy(importedModules[i], canonical))
43 copy->addImport(importCopy, INCLUDING, lineNumber); // HACK should this be INCLUDING?
44 else
45 {
46 //
47 // One of our imports failed its renaming. Abort construction of the
48 // renamed copy and mark it as bad. Let the module cache handle the
49 // clean up.
50 //
51 copy->markAsBad();
52 return copy;
53 }
54 }
55 finishCopy(copy, canonical);
56 return copy;
57 }
58
59 void
finishCopy(ImportModule * copy,Renaming * canonical)60 ImportModule::finishCopy(ImportModule* copy, Renaming* canonical)
61 {
62 Assert(!isBad(), "original module bad " << this);
63 copy->canonicalRenaming = canonical;
64 copy->baseModule = this;
65 addUser(copy);
66 //
67 // Copy our local contents, renaming it as we go, and flattening
68 // in our imports (but not statements).
69 //
70 copy->importSorts();
71 donateSorts2(copy, canonical);
72 copy->closeSortSet();
73
74 DebugAdvisory("finishCopy() done with sorts - from " << this << " to " << copy <<
75 " copy->isBad() = " << copy->isBad());
76 if (!(copy->isBad()))
77 {
78 copy->importOps();
79 donateOps2(copy, canonical);
80 DebugAdvisory("finishCopy() done with ops - from " << this << " to " << copy <<
81 " copy->isBad() = " << copy->isBad());
82 if (!(copy->isBad()))
83 {
84 copy->closeSignature();
85 copy->fixUpImportedOps();
86 fixUpDonatedOps2(copy, canonical);
87 DebugAdvisory("finishCopy() done with fixups - from " << this << " to " << copy <<
88 " copy->isBad() = " << copy->isBad());
89 if (!(copy->isBad()))
90 {
91 copy->closeFixUps();
92 //
93 // Statements are not copied so we have no local statements.
94 //
95 copy->localStatementsComplete();
96 }
97 }
98 }
99 //
100 // Reset phase counter in each imported module and return copy.
101 //
102 copy->resetImports();
103 }
104
105 Sort*
localSort(ImportModule * copy,Renaming * renaming,const Sort * sort)106 ImportModule::localSort(ImportModule* copy, Renaming* renaming, const Sort* sort)
107 {
108 return (sort->index() == Sort::KIND) ?
109 localSort2(copy, renaming, sort->component()->sort(1))->component()->sort(Sort::KIND) :
110 localSort2(copy, renaming, sort);
111 }
112
113 Sort*
localSort2(ImportModule * copy,Renaming * renaming,const Sort * sort)114 ImportModule::localSort2(ImportModule* copy, Renaming* renaming, const Sort* sort)
115 {
116 int id = sort->id();
117 if (renaming != 0)
118 id = renaming->renameSort(id);
119 Sort* ts = copy->findSort(id);
120 Assert(ts != 0, "couldn't find sort " << QUOTE(Token::sortName(id)) <<
121 " renamed from " << QUOTE(sort) << " in module " << copy);
122 return ts;
123 }
124
125 void
donateSorts2(ImportModule * copy,Renaming * renaming)126 ImportModule::donateSorts2(ImportModule* copy, Renaming* renaming)
127 {
128 Assert(!isBad(), "original module bad " << this);
129 //
130 // Donate our sorts, after a possible renaming.
131 //
132 bool moduleDonatingToTheory = copy->isTheory() && !isTheory();
133 const Vector<Sort*>& sorts = getSorts();
134 for (int i = nrImportedSorts; i < nrUserSorts; i++)
135 {
136 Sort* original = sorts[i];
137 int id = original->id();
138 if (renaming != 0)
139 id = renaming->renameSort(id);
140 Sort* sort = copy->findSort(id);
141 if (sort == 0)
142 {
143 sort = copy->addSort(id);
144 sort->setLineNumber(original->getLineNumber());
145 }
146 else
147 {
148 if (copy->isTheory() &&
149 (moduleDonatingToTheory != copy->sortDeclaredInModule.contains(sort->getIndexWithinModule())))
150 {
151 //
152 // A theory is getting the same sort from a module and a theory.
153 // This is a nasty situation that can cause various inconsistancies
154 // down the road since sorts from modules are handled differently
155 // to sorts from thoeries; so we handle it harshly.
156 //
157 IssueWarning(*copy << ": sort " << QUOTE(original) <<
158 " has been imported from both " << *original <<
159 " and " << *sort <<
160 ". Since it is imported from both a module and a theory, this renders theory " <<
161 QUOTE(copy) << " unusable.");
162 copy->markAsBad();
163 }
164 else
165 {
166 IssueAdvisory(*copy << ": sort " << QUOTE(original) <<
167 " has been imported from both " << *original <<
168 " and " << *sort << '.');
169 }
170 }
171 if (moduleDonatingToTheory)
172 copy->sortDeclaredInModule.insert(sort->getIndexWithinModule());
173 }
174 //
175 // Donate our subsort relations, after a possible renaming.
176 //
177 for (int i = 0; i < nrUserSorts; i++)
178 {
179 int nrImports = getNrImportedSubsorts(i);
180 const Sort* s = sorts[i];
181 const Vector<Sort*>& subsorts = s->getSubsorts();
182 int nrSubsorts = subsorts.length();
183 if (nrSubsorts > nrImports)
184 {
185 Sort* ts = localSort2(copy, renaming, s);
186 for (int j = nrImports; j < nrSubsorts; j++)
187 ts->insertSubsort(localSort2(copy, renaming, subsorts[j]));
188 }
189 }
190 }
191
192 void
donateOps2(ImportModule * copy,Renaming * renaming)193 ImportModule::donateOps2(ImportModule* copy, Renaming* renaming)
194 {
195 DebugAdvisory("donateOps2(), from " << this << " to " << copy);
196 Assert(!isBad(), "original module bad " << this);
197
198 bool moduleDonatingToTheory = copy->isTheory() && !isTheory();
199
200 Vector<int> gather;
201 Vector<Sort*> domainAndRange;
202 Vector<int> emptyStrategy;
203 //
204 // Handle our regular operators.
205 //
206 const Vector<Symbol*>& symbols = getSymbols();
207 for (int i = 0; i < nrUserSymbols; i++)
208 {
209 int nrImportedDeclarations = getNrImportedDeclarations(i);
210 int nrUserDeclarations = nrUserDecls[i];
211 if (nrUserDeclarations > nrImportedDeclarations)
212 {
213 //
214 // Need to donate some declarations for this symbol.
215 //
216 Symbol* symbol = symbols[i];
217 SymbolType symbolType = getSymbolType(symbol);
218 Assert(!(symbolType.isCreatedOnTheFly()),
219 "unexpected variable/sort test/polymorph instance " << symbol);
220
221 Token name;
222 int prec = DEFAULT;
223 const Vector<int>* format;
224
225 int index = (renaming == 0) ? NONE : renaming->renameOp(symbol); // index of renaming that applies to symbol
226 if (index == NONE)
227 {
228 name.tokenize(symbol->id(), symbol->getLineNumber());
229 prec = symbolType.hasFlag(SymbolType::PREC) ? getPrec(symbol) : DEFAULT;
230 if (symbolType.hasFlag(SymbolType::GATHER))
231 getGather(symbol, gather);
232 else
233 gather.clear();
234 format = &(getFormat(symbol));
235 }
236 else
237 {
238 int newName = renaming->getOpTo(index);
239 DebugAdvisory("Old symbol = " << symbol << " newName = " << Token::name(newName));
240 name.tokenize(newName, symbol->getLineNumber());
241 prec = renaming->getPrec(index);
242 symbolType.assignFlags(SymbolType::PREC, prec != DEFAULT);
243 gather = renaming->getGather(index); // deep copy
244 symbolType.assignFlags(SymbolType::GATHER, !gather.empty());
245 format = &(renaming->getFormat(index));
246 symbolType.assignFlags(SymbolType::FORMAT, !format->empty());
247 }
248
249 const Vector<OpDeclaration>& opDecls = symbol->getOpDeclarations();
250 int domainAndRangeLength = opDecls[0].getDomainAndRange().length();
251 domainAndRange.resize(domainAndRangeLength);
252 const Vector<int>& strategy = symbolType.hasFlag(SymbolType::STRAT) ?
253 symbol->getStrategy() : emptyStrategy;
254 const NatSet& frozen = symbol->getFrozen();
255
256 bool originator;
257 for (int j = nrImportedDeclarations; j < nrUserDeclarations; j++)
258 {
259 const Vector<Sort*>& oldDomainAndRange = opDecls[j].getDomainAndRange();
260 for (int k = 0; k < domainAndRangeLength; k++)
261 domainAndRange[k] = localSort(copy, renaming, oldDomainAndRange[k]);
262 symbolType.assignFlags(SymbolType::CTOR, opDecls[j].isConstructor());
263 Symbol* newSymbol = copy->addOpDeclaration(name, // BUG: name has codeNr = -1
264 domainAndRange,
265 symbolType,
266 strategy,
267 frozen,
268 prec,
269 gather,
270 *format,
271 getMetadata(symbol, j),
272 originator);
273 if (j == 0)
274 {
275 if (originator)
276 {
277 if (symbolType.getBasicType() == SymbolType::BUBBLE)
278 copy->copyBubbleSpec(symbol, newSymbol);
279 }
280 else
281 {
282 IssueAdvisory(*copy << ": operator " << QUOTE(newSymbol) <<
283 " has been imported from both " << *newSymbol <<
284 " and " << *symbol << " with no common ancestor.");
285 }
286 }
287 else // we must have already imported some declarations
288 Assert(!originator, "bad origination of " << symbol);
289 if (moduleDonatingToTheory)
290 copy->opDeclaredInModule.insert(newSymbol->getIndexWithinModule());
291 }
292 }
293 }
294 //
295 // Now handle our polymorphic operators.
296 //
297 int nrPolymorphs = getNrPolymorphs();
298 for (int i = nrImportedPolymorphs; i < nrPolymorphs; i++)
299 {
300 Token name = getPolymorphName(i);
301 SymbolType symbolType = getPolymorphType(i);
302 int prec = DEFAULT;
303 const Vector<int>* format;
304
305 int index = (renaming == 0) ? NONE : renaming->renamePolymorph(name.code());
306 if (index == NONE)
307 {
308 prec = symbolType.hasFlag(SymbolType::PREC) ? getPolymorphPrec(i) : DEFAULT;
309 if (symbolType.hasFlag(SymbolType::GATHER))
310 getPolymorphGather(i, gather);
311 else
312 gather.clear();
313 format = &(getPolymorphFormat(i));
314 }
315 else
316 {
317 name.tokenize(renaming->getOpTo(index), name.lineNumber());
318 prec = renaming->getPrec(index);
319 symbolType.assignFlags(SymbolType::PREC, prec != DEFAULT);
320 gather = renaming->getGather(index); // deep copy
321 symbolType.assignFlags(SymbolType::GATHER, !gather.empty());
322 format = &(renaming->getFormat(index));
323 symbolType.assignFlags(SymbolType::FORMAT, !format->empty());
324 }
325
326 const Vector<Sort*>& oldDomainAndRange = getPolymorphDomainAndRange(i);
327 int domainAndRangeLength = oldDomainAndRange.length();
328 domainAndRange.resize(domainAndRangeLength);
329 for (int j = 0; j < domainAndRangeLength; j++)
330 {
331 Sort* s = oldDomainAndRange[j];
332 domainAndRange[j] = (s == 0) ? 0 : localSort(copy, renaming, s);
333 }
334
335 const Vector<int>& strategy = symbolType.hasFlag(SymbolType::STRAT) ?
336 getPolymorphStrategy(i) : emptyStrategy;
337
338 int copyIndex = copy->addPolymorph(name,
339 domainAndRange,
340 symbolType,
341 strategy,
342 getPolymorphFrozen(i),
343 prec,
344 gather,
345 *format,
346 getPolymorphMetadata(i));
347 if (moduleDonatingToTheory)
348 copy->polymorphDeclaredInModule.insert(copyIndex);
349 }
350 }
351
352 void
fixUpDonatedOps2(ImportModule * copy,Renaming * renaming)353 ImportModule::fixUpDonatedOps2(ImportModule* copy, Renaming* renaming)
354 {
355 //
356 // The map from imported module's symbols to importing module's symbols
357 // is built dynamically.
358 //
359 ImportTranslation importTranslation(copy, renaming);
360 //
361 // Handle our regular operators.
362 //
363 const Vector<Symbol*>& symbols = getSymbols();
364 for (int i = 0; i < nrUserSymbols; i++)
365 {
366 int nrImportedDeclarations = getNrImportedDeclarations(i);
367 if (nrUserDecls[i] > nrImportedDeclarations)
368 {
369 //
370 // We donated some declarations for this symbol so do
371 // an incremental fixup if needed.
372 //
373 Symbol* symbol = symbols[i];
374 SymbolType st = getSymbolType(symbol);
375 if (st.hasFlag(SymbolType::LEFT_ID | SymbolType::RIGHT_ID))
376 {
377 BinarySymbol* ns = safeCast(BinarySymbol*, importTranslation.translate(symbol));
378 if (ns->getIdentity() == 0)
379 {
380 Term* id = safeCast(BinarySymbol*, symbol)->getIdentity();
381 Assert(id != 0, "missing identity");
382 ns->setIdentity(id->deepCopy(&importTranslation));
383 }
384 }
385
386 if (st.hasAttachments())
387 importTranslation.translate(symbol)->copyAttachments(symbol, &importTranslation);
388 else if (st.getBasicType() == SymbolType::BUBBLE)
389 copy->copyFixUpBubbleSpec(symbol, &importTranslation);
390 }
391 }
392 //
393 // Now handle our polymorphic operators.
394 //
395 {
396 Vector<Sort*> domainAndRange;
397
398 int nrPolymorphs = getNrPolymorphs();
399 for (int i = nrImportedPolymorphs; i < nrPolymorphs; i++)
400 {
401 //
402 // Get polymorph name.
403 //
404 int id = getPolymorphName(i).code();
405 if (renaming != 0)
406 {
407 int index = renaming->renamePolymorph(id);
408 if (index != NONE)
409 id = renaming->getOpTo(index);
410 }
411 //
412 // Get polymorph domain and range.
413 //
414 const Vector<Sort*>& oldDomainAndRange = getPolymorphDomainAndRange(i);
415 int domainAndRangeLength = oldDomainAndRange.length();
416 domainAndRange.resize(domainAndRangeLength);
417 for (int j = 0; j < domainAndRangeLength; j++)
418 {
419 Sort* s = oldDomainAndRange[j];
420 domainAndRange[j] = (s == 0) ? 0 : localSort(copy, renaming, s);
421 }
422
423 int donatedCopyIndex = copy->findPolymorphIndex(id, domainAndRange);
424 Assert(donatedCopyIndex != NONE, "missing polymorph");
425 copy->copyFixUpPolymorph(donatedCopyIndex, this, i, &importTranslation);
426 }
427 }
428 }
429
430 void
localStatementsComplete()431 ImportModule::localStatementsComplete()
432 {
433 nrOriginalMembershipAxioms = getSortConstraints().length();
434 nrOriginalEquations = getEquations().length();
435 nrOriginalRules = getRules().length();
436
437 FOR_EACH_CONST(i, Vector<ImportModule*>, importedModules)
438 labels.insert((*i)->labels.begin(), (*i)->labels.end());
439 if (canonicalRenaming == 0)
440 {
441 {
442 FOR_EACH_CONST(i, Vector<SortConstraint*>, getSortConstraints())
443 {
444 int id = (*i)->getLabel().id();
445 if (id != NONE)
446 labels.insert(id);
447 }
448 }
449 {
450 FOR_EACH_CONST(i, Vector<Equation*>, getEquations())
451 {
452 int id = (*i)->getLabel().id();
453 if (id != NONE)
454 labels.insert(id);
455 }
456 }
457 {
458 FOR_EACH_CONST(i, Vector<Rule*>, getRules())
459 {
460 int id = (*i)->getLabel().id();
461 if (id != NONE)
462 labels.insert(id);
463 }
464 }
465 }
466 else
467 {
468 FOR_EACH_CONST(i, set<int>, baseModule->labels)
469 labels.insert(canonicalRenaming->renameLabel(*i));
470 }
471 }
472