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 DagNode*
upQid(int id,PointerMap & qidMap)24 MetaLevel::upQid(int id, PointerMap& qidMap)
25 {
26 void* p = const_cast<void*>(static_cast<const void*>(Token::name(id)));
27 DagNode *d = static_cast<DagNode*>(qidMap.getMap(p));
28 if (d == 0)
29 {
30 d = new QuotedIdentifierDagNode(qidSymbol, Token::backQuoteSpecials(id));
31 (void) qidMap.setMap(p, d);
32 }
33 return d;
34 }
35
36 DagNode*
upType(Sort * sort,PointerMap & qidMap)37 MetaLevel::upType(Sort* sort, PointerMap& qidMap)
38 {
39 int id = sort->id();
40 if (sort->index() == Sort::KIND)
41 {
42 string fullName("`[");
43 ConnectedComponent* component = sort->component();
44 int nrMaxSorts = component->nrMaximalSorts();
45 for (int i = 1; i <= nrMaxSorts; i++)
46 {
47 fullName += Token::name(component->sort(i)->id());
48 fullName += (i == nrMaxSorts) ? "`]" : "`,";
49 }
50 id = Token::encode(fullName.c_str());
51 }
52 return upQid(id, qidMap);
53 }
54
55 DagNode*
upJoin(int id,Sort * sort,char sep,PointerMap & qidMap)56 MetaLevel::upJoin(int id, Sort* sort, char sep, PointerMap& qidMap)
57 {
58 Assert(sort != 0, "null sort");
59 string fullName(Token::name(id));
60 fullName += sep;
61 if (sort->index() == Sort::KIND)
62 {
63 fullName += "`[";
64 ConnectedComponent* component = sort->component();
65 int nrMaxSorts = component->nrMaximalSorts();
66 for (int i = 1; i <= nrMaxSorts; i++)
67 {
68 fullName += Token::name(component->sort(i)->id());
69 fullName += (i == nrMaxSorts) ? "`]" : "`,";
70 }
71 }
72 else
73 fullName += Token::name(sort->id());
74 return upQid(Token::encode(fullName.c_str()), qidMap);
75 }
76
77 local_inline DagNode*
upConstant(int id,Sort * sort,PointerMap & qidMap)78 MetaLevel::upConstant(int id, Sort* sort, PointerMap& qidMap)
79 {
80 return upJoin(id, sort, '.', qidMap);
81 }
82
83 DagNode*
upConstant(int id,DagNode * d,PointerMap & qidMap)84 MetaLevel::upConstant(int id, DagNode* d, PointerMap& qidMap)
85 {
86 Sort* sort = d->getSort();
87 if (sort == 0)
88 {
89 //
90 // Can happen since sorts are not calculated in unifiers.
91 // Fortunately there shouldn't be any membership axioms involved
92 // in a unification problem and the precise sorts of constants is
93 // non-critical for disambiguation.
94 // So we temporarily compute a base sort.
95 //
96 Symbol* s = d->symbol();
97 s->computeBaseSort(d);
98 sort = s->rangeComponent()->sort(d->getSortIndex());
99 d->setSortIndex(Sort::SORT_UNKNOWN);
100 }
101 return upJoin(id, sort, '.', qidMap);
102 }
103
104 inline DagNode*
upVariable(int id,Sort * sort,PointerMap & qidMap)105 MetaLevel::upVariable(int id, Sort* sort, PointerMap& qidMap)
106 {
107 //
108 // id might be flagged (in the disjoint unification case) so we always unflag it.
109 //
110 return upJoin(Token::unflaggedCode(id), sort, ':', qidMap);
111 }
112
113 DagNode*
upDagNode(DagNode * dagNode,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)114 MetaLevel::upDagNode(DagNode* dagNode,
115 MixfixModule* m,
116 PointerMap& qidMap,
117 PointerMap& dagNodeMap)
118 {
119 Assert(dagNode != 0, "null dagNode");
120 Vector<DagNode*> args(2); // can't be static!
121 //
122 // See if we have already up'd this dag node via a different path.
123 //
124 DagNode *d = static_cast<DagNode*>(dagNodeMap.getMap(dagNode));
125 if (d != 0)
126 return d;
127 //
128 // Examine symbol to see if we have a special representation with its own
129 // conversion scheme.
130 //
131 Symbol* s = dagNode->symbol();
132 switch (m->getSymbolType(s).getBasicType())
133 {
134 case SymbolType::QUOTED_IDENTIFIER:
135 {
136 int id = static_cast<QuotedIdentifierDagNode*>(dagNode)->getIdIndex();
137 d = upConstant(Token::quoteNameCode(id), dagNode, qidMap);
138 break;
139 }
140 case SymbolType::STRING:
141 {
142 string result;
143 Token::ropeToString(static_cast<StringDagNode*>(dagNode)->getValue(), result);
144 d = upConstant(Token::encode(result.c_str()), dagNode, qidMap);
145 break;
146 }
147 case SymbolType::FLOAT:
148 {
149 double mf = static_cast<FloatDagNode*>(dagNode)->getValue();
150 d = upConstant(Token::doubleToCode(mf), dagNode, qidMap);
151 break;
152 }
153 case SymbolType::SMT_NUMBER_SYMBOL:
154 {
155 const mpq_class& value = safeCast(SMT_NumberDagNode*, dagNode)->getValue();
156 d = upSMT_Number(value, s, m, qidMap);
157 break;
158 }
159 case SymbolType::VARIABLE:
160 {
161 VariableDagNode* v = safeCast(VariableDagNode*, dagNode);
162 int id = (variableGenerator == 0) ? v->id() :
163 variableGenerator->getFreshVariableName(variableBase + v->getIndex());
164 Sort* sort = safeCast(VariableSymbol*, dagNode->symbol())->getSort();
165 d = upVariable(id, sort, qidMap);
166 break;
167 }
168 default:
169 {
170 int nrArgs = s->arity();
171 if (nrArgs == 0)
172 d = upConstant(s->id(), dagNode, qidMap);
173 else
174 {
175 args[0] = upQid(m->getSymbolType(s).hasFlag(SymbolType::ITER) ?
176 iterToken(dagNode) : s->id(),
177 qidMap);
178 DagArgumentIterator a(*dagNode);
179 if (nrArgs == 1)
180 args[1] = upDagNode(a.argument(), m, qidMap, dagNodeMap);
181 else
182 {
183 //
184 // nrArgs is only a suggestion - flattened assoc operators may have more args.
185 //
186 Vector<DagNode*> args2(0, nrArgs); // can't be static!
187 for (; a.valid(); a.next())
188 args2.append(upDagNode(a.argument(), m, qidMap, dagNodeMap));
189 args[1] = metaArgSymbol->makeDagNode(args2);
190 }
191 d = metaTermSymbol->makeDagNode(args);
192 }
193 break;
194 }
195 }
196 (void) dagNodeMap.setMap(dagNode, d);
197 return d;
198 }
199
200 DagNode*
upTerm(const Term * term,MixfixModule * m,PointerMap & qidMap)201 MetaLevel::upTerm(const Term* term, MixfixModule* m, PointerMap& qidMap)
202 {
203 Assert(term != 0, "null term");
204 Vector<DagNode*> args(2); // can't be static!
205 //
206 // Examine symbol to see if we have a special representation with its own
207 // conversion scheme.
208 //
209
210 Symbol* s = term->symbol();
211 switch (m->getSymbolType(s).getBasicType())
212 {
213 case SymbolType::QUOTED_IDENTIFIER:
214 {
215 int id = static_cast<const QuotedIdentifierTerm*>(term)->getIdIndex();
216 return upConstant(Token::quoteNameCode(id), MixfixModule::disambiguatorSort(term), qidMap);
217 }
218 case SymbolType::STRING:
219 {
220 string result;
221 Token::ropeToString(static_cast<const StringTerm*>(term)->getValue(), result);
222 return upConstant(Token::encode(result.c_str()), MixfixModule::disambiguatorSort(term), qidMap);
223 }
224 case SymbolType::FLOAT:
225 {
226 double mf = static_cast<const FloatTerm*>(term)->getValue();
227 return upConstant(Token::doubleToCode(mf), MixfixModule::disambiguatorSort(term), qidMap);
228 }
229 case SymbolType::SMT_NUMBER_SYMBOL:
230 {
231 const mpq_class& value = safeCast(const SMT_NumberTerm*, term)->getValue();
232 return upSMT_Number(value, s, m, qidMap);
233 }
234 case SymbolType::VARIABLE:
235 {
236 const VariableTerm* vt = safeCast(const VariableTerm*, term);
237 return upVariable(vt->id(), vt->getSort(), qidMap);
238 }
239 default:
240 {
241 int nrArgs = s->arity();
242 if (nrArgs == 0)
243 return upConstant(s->id(), MixfixModule::disambiguatorSort(term), qidMap);
244 else
245 {
246 int id = s->id();
247 if (m->getSymbolType(s).hasFlag(SymbolType::ITER))
248 {
249 const mpz_class& number = safeCast(const S_Term*, term)->getNumber();
250 if (number > 1)
251 {
252 string tmp(Token::name(id));
253 tmp += '^';
254 char* str = mpz_get_str(0, 10, number.get_mpz_t());
255 tmp += str;
256 free(str);
257 id = Token::encode(tmp.c_str());
258 }
259 }
260 args[0] = upQid(id, qidMap);
261 ArgumentIterator a(*(const_cast<Term*>(term)));
262 if (nrArgs == 1)
263 args[1] = upTerm(a.argument(), m, qidMap);
264 else
265 {
266 //
267 // nrArgs is only a suggestion - flattened assoc operators may have more args.
268 //
269 Vector<DagNode*> args2(0, nrArgs); // can't be static!
270 for (; a.valid(); a.next())
271 args2.append(upTerm(a.argument(), m, qidMap));
272 args[1] = metaArgSymbol->makeDagNode(args2);
273 }
274 return metaTermSymbol->makeDagNode(args);
275 }
276 }
277 }
278 }
279
280 int
iterToken(DagNode * dagNode)281 MetaLevel::iterToken(DagNode* dagNode)
282 {
283 int id = dagNode->symbol()->id();
284 const mpz_class& number = safeCast(S_DagNode*, dagNode)->getNumber();
285 if (number == 1)
286 return id;
287 string tmp(Token::name(id));
288 tmp += '^';
289 char* str = mpz_get_str(0, 10, number.get_mpz_t());
290 tmp += str;
291 free(str);
292 return Token::encode(tmp.c_str());
293 }
294
295 DagNode*
upContext(DagNode * dagNode,MixfixModule * m,DagNode * hole,PointerMap & qidMap,PointerMap & dagNodeMap)296 MetaLevel::upContext(DagNode* dagNode,
297 MixfixModule* m,
298 DagNode* hole,
299 PointerMap& qidMap,
300 PointerMap& dagNodeMap)
301 {
302 Assert(dagNode != 0, "null dagNode");
303 //
304 // See if we have already up'd this dag node via a different path.
305 //
306 if (DagNode *d = static_cast<DagNode*>(dagNodeMap.getMap(dagNode)))
307 return d;
308 //
309 // See if our node is the hole.
310 //
311 if (dagNode == hole)
312 return holeSymbol->makeDagNode();
313 //
314 // Constants cannot contain the hole.
315 //
316 Symbol* s = dagNode->symbol();
317 int nrArgs = s->arity();
318 if (nrArgs == 0)
319 return upDagNode(dagNode, m, qidMap, dagNodeMap);
320 //
321 // Usual case.
322 //
323 Vector<DagNode*> args(2); // can't be static!
324 args[0] = upQid(m->getSymbolType(s).hasFlag(SymbolType::ITER) ?
325 iterToken(dagNode) : s->id(),
326 qidMap);
327 DagArgumentIterator a(*dagNode);
328 if (nrArgs == 1)
329 args[1] = upContext(a.argument(), m, hole, qidMap, dagNodeMap);
330 else
331 {
332 Vector<DagNode*> args2(0, nrArgs); // can't be static!
333 for (; a.valid(); a.next())
334 args2.append(upContext(a.argument(), m, hole, qidMap, dagNodeMap));
335 args[1] = metaArgSymbol->makeDagNode(args2);
336 }
337 DagNode* d = metaTermSymbol->makeDagNode(args);
338 (void) dagNodeMap.setMap(dagNode, d);
339 return d;
340 }
341
342 DagNode*
upResultPair(DagNode * dagNode,MixfixModule * m)343 MetaLevel::upResultPair(DagNode* dagNode, MixfixModule* m)
344 {
345 Assert(dagNode != 0, "null dagNode");
346 static Vector<DagNode*> args(2);
347 PointerMap qidMap;
348 PointerMap dagNodeMap;
349 args[0] = upDagNode(dagNode, m, qidMap, dagNodeMap);
350 args[1] = upType(dagNode->getSort(), qidMap);
351 return resultPairSymbol->makeDagNode(args);
352 }
353
354 DagNode*
upResultPair(Term * term,MixfixModule * m)355 MetaLevel::upResultPair(Term* term, MixfixModule* m)
356 {
357 Assert(term != 0, "null term");
358 static Vector<DagNode*> args(2);
359 PointerMap qidMap;
360 args[0] = upTerm(term, m, qidMap);
361 args[1] = upType(term->getSort(), qidMap);
362 return resultPairSymbol->makeDagNode(args);
363 }
364
365 DagNode*
upResultTriple(DagNode * dagNode,const Substitution & substitution,const VariableInfo & variableInfo,MixfixModule * m)366 MetaLevel::upResultTriple(DagNode* dagNode,
367 const Substitution& substitution,
368 const VariableInfo& variableInfo,
369 MixfixModule* m)
370 {
371 Assert(dagNode != 0, "null dagNode");
372 static Vector<DagNode*> args(3);
373 PointerMap qidMap;
374 PointerMap dagNodeMap;
375 args[0] = upDagNode(dagNode, m, qidMap, dagNodeMap);
376 args[1] = upType(dagNode->getSort(), qidMap);
377 args[2] = upSubstitution(substitution, variableInfo, m, qidMap, dagNodeMap);
378 return resultTripleSymbol->makeDagNode(args);
379 }
380
381 DagNode*
upResult4Tuple(DagNode * dagNode,const Substitution & substitution,const VariableInfo & variableInfo,DagNode * metaContext,MixfixModule * m)382 MetaLevel::upResult4Tuple(DagNode* dagNode,
383 const Substitution& substitution,
384 const VariableInfo& variableInfo,
385 DagNode* metaContext,
386 MixfixModule* m)
387 {
388 Assert(dagNode != 0, "null dagNode");
389 static Vector<DagNode*> args(4);
390 PointerMap qidMap;
391 PointerMap dagNodeMap;
392 args[0] = upDagNode(dagNode, m, qidMap, dagNodeMap);
393 args[1] = upType(dagNode->getSort(), qidMap);
394 args[2] = upSubstitution(substitution, variableInfo, m, qidMap, dagNodeMap);
395 args[3] = metaContext;
396 return result4TupleSymbol->makeDagNode(args);
397 }
398
399 DagNode*
upUnificationPair(const Substitution & substitution,const VariableInfo & variableInfo,const mpz_class & variableIndex,MixfixModule * m)400 MetaLevel::upUnificationPair(const Substitution& substitution,
401 const VariableInfo& variableInfo,
402 const mpz_class& variableIndex,
403 MixfixModule* m)
404 {
405 PointerMap qidMap;
406 PointerMap dagNodeMap;
407 Vector<DagNode*> args(2);
408 args[0] = upSubstitution(substitution, variableInfo, m, qidMap, dagNodeMap);
409 args[1] = succSymbol->makeNatDag(variableIndex);
410 return unificationPairSymbol->makeDagNode(args);
411 }
412
413 DagNode*
upUnificationTriple(const Substitution & substitution,const VariableInfo & variableInfo,const mpz_class & variableIndex,MixfixModule * m)414 MetaLevel::upUnificationTriple(const Substitution& substitution,
415 const VariableInfo& variableInfo,
416 const mpz_class& variableIndex,
417 MixfixModule* m)
418 {
419 PointerMap qidMap;
420 PointerMap dagNodeMap;
421 Vector<DagNode*> args(3);
422 upDisjointSubstitutions(substitution,
423 variableInfo,
424 m,
425 qidMap,
426 dagNodeMap,
427 args[0],
428 args[1]);
429 args[2] = succSymbol->makeNatDag(variableIndex);
430 return unificationTripleSymbol->makeDagNode(args);
431 }
432
433
434 void
upDisjointSubstitutions(const Substitution & substitution,const VariableInfo & variableInfo,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap,DagNode * & left,DagNode * & right)435 MetaLevel::upDisjointSubstitutions(const Substitution& substitution,
436 const VariableInfo& variableInfo,
437 MixfixModule* m,
438 PointerMap& qidMap,
439 PointerMap& dagNodeMap,
440 DagNode*& left,
441 DagNode*& right)
442 {
443 int nrVariables = variableInfo.getNrRealVariables();
444 Vector<DagNode*> leftArgs(0, nrVariables);
445 Vector<DagNode*> rightArgs(0, nrVariables);
446 for (int i = 0; i < nrVariables; i++)
447 {
448 VariableTerm* variable = safeCast(VariableTerm*, variableInfo.index2Variable(i));
449 DagNode* d = upAssignment(variable,
450 substitution.value(i),
451 m,
452 qidMap,
453 dagNodeMap);
454 if (Token::isFlagged(variable->id()))
455 rightArgs.append(d);
456 else
457 leftArgs.append(d);
458 }
459 int nrLeftArgs = leftArgs.size();
460 if (nrLeftArgs == 0)
461 left = emptySubstitutionSymbol->makeDagNode();
462 else if (nrLeftArgs == 1)
463 left = leftArgs[0];
464 else
465 left = substitutionSymbol->makeDagNode(leftArgs);
466 int nrRightArgs = rightArgs.size();
467 if (nrRightArgs == 0)
468 right = emptySubstitutionSymbol->makeDagNode();
469 else if (nrRightArgs == 1)
470 right = rightArgs[0];
471 else
472 right = substitutionSymbol->makeDagNode(rightArgs);
473 }
474
475 DagNode*
upSubstitution(const Substitution & substitution,const VariableInfo & variableInfo,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)476 MetaLevel::upSubstitution(const Substitution& substitution,
477 const VariableInfo& variableInfo,
478 MixfixModule* m,
479 PointerMap& qidMap,
480 PointerMap& dagNodeMap)
481 {
482 int nrVariables = variableInfo.getNrRealVariables();
483 if (nrVariables == 0)
484 return emptySubstitutionSymbol->makeDagNode();
485 if (nrVariables == 1)
486 {
487 return upAssignment(variableInfo.index2Variable(0),
488 substitution.value(0),
489 m,
490 qidMap,
491 dagNodeMap);
492 }
493 Vector<DagNode*> args(nrVariables);
494 for (int i = 0; i < nrVariables; i++)
495 {
496 args[i] = upAssignment(variableInfo.index2Variable(i),
497 substitution.value(i),
498 m,
499 qidMap,
500 dagNodeMap);
501 }
502 return substitutionSymbol->makeDagNode(args);
503 }
504
505 DagNode*
upAssignment(const Term * variable,DagNode * value,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)506 MetaLevel::upAssignment(const Term* variable,
507 DagNode* value,
508 MixfixModule* m,
509 PointerMap& qidMap,
510 PointerMap& dagNodeMap)
511 {
512 static Vector<DagNode*> args(2);
513 args[0] = upTerm(variable, m, qidMap);
514 args[1] = upDagNode(value, m, qidMap, dagNodeMap);
515 return assignmentSymbol->makeDagNode(args);
516 }
517
518 DagNode*
upAssignment(DagNode * variable,DagNode * value,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)519 MetaLevel::upAssignment(DagNode* variable,
520 DagNode* value,
521 MixfixModule* m,
522 PointerMap& qidMap,
523 PointerMap& dagNodeMap)
524 {
525 static Vector<DagNode*> args(2);
526 args[0] = upDagNode(variable, m, qidMap, dagNodeMap);
527 args[1] = upDagNode(value, m, qidMap, dagNodeMap);
528 return assignmentSymbol->makeDagNode(args);
529 }
530
531 DagNode*
upSmtSubstitution(const Substitution & substitution,const VariableInfo & variableInfo,const NatSet & smtVariables,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)532 MetaLevel::upSmtSubstitution(const Substitution& substitution,
533 const VariableInfo& variableInfo,
534 const NatSet& smtVariables,
535 MixfixModule* m,
536 PointerMap& qidMap,
537 PointerMap& dagNodeMap)
538 {
539 int nrVariables = variableInfo.getNrRealVariables();
540 Vector<DagNode*> args;
541
542 for (int i = 0; i < nrVariables; i++)
543 {
544 //
545 // SMT variables are constrained rather than bound.
546 //
547 if (!smtVariables.contains(i))
548 {
549 args.append(upAssignment(variableInfo.index2Variable(0),
550 substitution.value(0),
551 m,
552 qidMap,
553 dagNodeMap));
554 }
555 }
556
557 int nrBindings = args.size();
558 if (nrBindings == 0)
559 return emptySubstitutionSymbol->makeDagNode();
560 if (nrBindings == 1)
561 return args[0];
562 return substitutionSymbol->makeDagNode(args);
563 }
564
565 DagNode*
upSmtResult(DagNode * state,const Substitution & substitution,const VariableInfo & variableInfo,const NatSet & smtVariables,DagNode * constraint,const mpz_class & variableNumber,MixfixModule * m)566 MetaLevel::upSmtResult(DagNode* state,
567 const Substitution& substitution,
568 const VariableInfo& variableInfo,
569 const NatSet& smtVariables,
570 DagNode* constraint,
571 const mpz_class& variableNumber,
572 MixfixModule* m)
573 {
574 Assert(state != 0, "null state");
575 Assert(constraint != 0, "null constraint");
576 Vector<DagNode*> args(4);
577 PointerMap qidMap;
578 PointerMap dagNodeMap;
579 args[0] = upDagNode(state, m, qidMap, dagNodeMap);
580 args[1] = upSmtSubstitution(substitution,
581 variableInfo,
582 smtVariables,
583 m,
584 qidMap,
585 dagNodeMap);
586 args[2] = upDagNode(constraint, m, qidMap, dagNodeMap);
587 args[3] = succSymbol->makeNatDag(variableNumber);
588 return smtResultSymbol->makeDagNode(args);
589 }
590
591 DagNode*
upSmtFailure()592 MetaLevel::upSmtFailure()
593 {
594 return smtFailureSymbol->makeDagNode();
595 }
596
597 DagNode*
upFailurePair()598 MetaLevel::upFailurePair()
599 {
600 return failure2Symbol->makeDagNode();
601 }
602
603 DagNode*
upFailureTriple()604 MetaLevel::upFailureTriple()
605 {
606 return failure3Symbol->makeDagNode();
607 }
608
609 DagNode*
upNoUnifierPair(bool incomplete)610 MetaLevel::upNoUnifierPair(bool incomplete)
611 {
612 return (incomplete ? noUnifierIncompletePairSymbol : noUnifierPairSymbol)->makeDagNode();
613 }
614
615 DagNode*
upNoUnifierTriple(bool incomplete)616 MetaLevel::upNoUnifierTriple(bool incomplete)
617 {
618 return (incomplete ? noUnifierIncompleteTripleSymbol : noUnifierTripleSymbol)->makeDagNode();
619 }
620
621 DagNode*
upNoMatchSubst()622 MetaLevel::upNoMatchSubst()
623 {
624 return noMatchSubstSymbol->makeDagNode();
625 }
626
627 DagNode*
upNoMatchPair()628 MetaLevel::upNoMatchPair()
629 {
630 return noMatchPairSymbol->makeDagNode();
631 }
632
633 DagNode*
upMatchPair(const Substitution & substitution,const VariableInfo & variableInfo,DagNode * dagNode,DagNode * hole,MixfixModule * m)634 MetaLevel::upMatchPair(const Substitution& substitution,
635 const VariableInfo& variableInfo,
636 DagNode* dagNode,
637 DagNode* hole,
638 MixfixModule* m)
639 {
640 PointerMap qidMap;
641 PointerMap dagNodeMap;
642 static Vector<DagNode*> args(2);
643 args[0] = upSubstitution(substitution, variableInfo, m, qidMap, dagNodeMap);
644 args[1] = upContext(dagNode, m, hole, qidMap, dagNodeMap);
645 return matchPairSymbol->makeDagNode(args);
646 }
647
648 DagNode*
upFailure4Tuple()649 MetaLevel::upFailure4Tuple()
650 {
651 return failure4Symbol->makeDagNode();
652 }
653
654 DagNode*
upTrace(const RewriteSequenceSearch & state,MixfixModule * m)655 MetaLevel::upTrace(const RewriteSequenceSearch& state, MixfixModule* m)
656 {
657 Vector<int> steps;
658 for (int i = state.getStateNr(); i != 0; i = state.getStateParent(i))
659 steps.append(i);
660
661 int nrSteps = steps.size();
662 if (nrSteps == 0)
663 return nilTraceSymbol->makeDagNode();
664
665 Vector<DagNode*> args(nrSteps);
666 PointerMap qidMap;
667 PointerMap dagNodeMap;
668 int j = 0;
669 for (int i = nrSteps - 1; i >= 0; --i, ++j)
670 args[j] = upTraceStep(state, steps[i], m, qidMap, dagNodeMap);
671 return (nrSteps == 1) ? args[0] : traceSymbol->makeDagNode(args);
672 }
673
674 DagNode*
upTraceStep(const RewriteSequenceSearch & state,int stateNr,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)675 MetaLevel::upTraceStep(const RewriteSequenceSearch& state,
676 int stateNr,
677 MixfixModule* m,
678 PointerMap& qidMap,
679 PointerMap& dagNodeMap)
680 {
681 static Vector<DagNode*> args(3);
682 int parentNr = state.getStateParent(stateNr);
683 DagNode* dagNode = state.getStateDag(parentNr);
684 args[0] = upDagNode(dagNode, m, qidMap, dagNodeMap);
685 args[1] = upType(dagNode->getSort(), qidMap);
686 args[2] = upRl(state.getStateRule(stateNr), m, qidMap);
687 return traceStepSymbol->makeDagNode(args);
688 }
689
690 DagNode*
upFailureTrace()691 MetaLevel::upFailureTrace()
692 {
693 return failureTraceSymbol->makeDagNode();
694 }
695
696 DagNode*
upNoParse(int badTokenIndex)697 MetaLevel::upNoParse(int badTokenIndex)
698 {
699 static Vector<DagNode*> args(1);
700 args[0] = succSymbol->makeNatDag(badTokenIndex);
701 return noParseSymbol->makeDagNode(args);
702 }
703
704 DagNode*
upAmbiguity(Term * parse1,Term * parse2,MixfixModule * m)705 MetaLevel::upAmbiguity(Term* parse1, Term* parse2, MixfixModule* m)
706 {
707 Assert(parse1 != 0 && parse2 != 0, "null term");
708 static Vector<DagNode*> args(2);
709 static Vector<DagNode*> args2(2);
710 PointerMap qidMap;
711 args[0] = upTerm(parse1, m, qidMap);
712 args[1] = upType(parse1->getSort(), qidMap);
713 args2[0] = resultPairSymbol->makeDagNode(args);
714 args[0] = upTerm(parse2, m, qidMap);
715 args[1] = upType(parse2->getSort(), qidMap);
716 args2[1] = resultPairSymbol->makeDagNode(args);
717 return ambiguitySymbol->makeDagNode(args2);
718 }
719
720 DagNode*
upBool(bool value)721 MetaLevel::upBool(bool value)
722 {
723 return value ? trueTerm.getDag() : falseTerm.getDag();
724 }
725
726 DagNode*
upKindSet(const Vector<ConnectedComponent * > & kinds)727 MetaLevel::upKindSet(const Vector<ConnectedComponent*>& kinds)
728 {
729 int nrKinds = kinds.length();
730 if (nrKinds == 0)
731 return new FreeDagNode(emptySortSetSymbol);
732 PointerMap qidMap;
733 if (nrKinds == 1)
734 return upType(kinds[0]->sort(0), qidMap);
735 Vector<DagNode*> args(nrKinds);
736 for (int i = 0; i < nrKinds; i++)
737 args[i] = upType(kinds[i]->sort(0), qidMap);
738 return sortSetSymbol->makeDagNode(args);
739 }
740
741 DagNode*
upSortSet(const Vector<Sort * > & sorts)742 MetaLevel::upSortSet(const Vector<Sort*>& sorts)
743 {
744 PointerMap qidMap;
745 return upSortSet(sorts, 0, sorts.length(), qidMap);
746 }
747
748 DagNode*
upSortSet(const Vector<Sort * > & sorts,int begin,int nrSorts,PointerMap & qidMap)749 MetaLevel::upSortSet(const Vector<Sort*>& sorts,
750 int begin,
751 int nrSorts,
752 PointerMap& qidMap)
753 {
754 if (nrSorts == 0)
755 return new FreeDagNode(emptySortSetSymbol);
756 if (nrSorts == 1)
757 return upType(sorts[begin], qidMap);
758 Vector<DagNode*> args(nrSorts);
759 for (int i = 0; i < nrSorts; i++, begin++)
760 args[i] = upType(sorts[begin], qidMap);
761 return sortSetSymbol->makeDagNode(args);
762 }
763
764 DagNode*
upQidList(const Vector<int> & ids)765 MetaLevel::upQidList(const Vector<int>& ids)
766 {
767 PointerMap qidMap;
768 return upQidList(ids, qidMap);
769 }
770
771 DagNode*
upQidList(const Vector<int> & ids,PointerMap & qidMap)772 MetaLevel::upQidList(const Vector<int>& ids, PointerMap& qidMap)
773 {
774 int nrIds = ids.length();
775 if (nrIds == 0)
776 return new FreeDagNode(nilQidListSymbol);
777 if (nrIds == 1)
778 return new QuotedIdentifierDagNode(qidSymbol, Token::backQuoteSpecials(ids[0]));
779 Vector<DagNode*> args(nrIds);
780 for (int i = 0; i < nrIds; i++)
781 args[i] = upQid(ids[i], qidMap);
782 return qidListSymbol->makeDagNode(args);
783 }
784
785 DagNode*
upTypeListSet(const Vector<OpDeclaration> & opDecls,const NatSet & chosenDecls,PointerMap & qidMap)786 MetaLevel::upTypeListSet(const Vector<OpDeclaration>& opDecls,
787 const NatSet& chosenDecls,
788 PointerMap& qidMap)
789 {
790 Vector<DagNode*> args;
791 FOR_EACH_CONST(i, NatSet, chosenDecls)
792 args.append(upTypeList(opDecls[*i].getDomainAndRange(), true, qidMap));
793 int nrArgs = args.size();
794 if (nrArgs == 0)
795 return new FreeDagNode(emptySortSetSymbol);
796 if (nrArgs == 1)
797 return args[0];
798 return sortSetSymbol->makeDagNode(args);
799 }
800
801 DagNode*
upTypeList(const Vector<Sort * > & types,bool omitLast,PointerMap & qidMap)802 MetaLevel::upTypeList(const Vector<Sort*>& types,
803 bool omitLast,
804 PointerMap& qidMap)
805 {
806 int nrTypes = types.size();
807 if (omitLast)
808 --nrTypes;
809 if (nrTypes == 0)
810 return new FreeDagNode(nilQidListSymbol);
811 if (nrTypes == 1)
812 return upType(types[0], qidMap);
813 Vector<DagNode*> args(nrTypes);
814 for (int i = 0; i < nrTypes; ++i)
815 args[i] = upType(types[i], qidMap);
816 return qidListSymbol->makeDagNode(args);
817 }
818
819 DagNode*
upSubstitution(const Vector<DagNode * > & substitution,const NarrowingVariableInfo & variableInfo,int nrVariables,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap)820 MetaLevel::upSubstitution(const Vector<DagNode*>& substitution,
821 const NarrowingVariableInfo& variableInfo,
822 int nrVariables,
823 MixfixModule* m,
824 PointerMap& qidMap,
825 PointerMap& dagNodeMap)
826 {
827 if (nrVariables == 0)
828 return emptySubstitutionSymbol->makeDagNode();
829 else if (nrVariables == 1)
830 {
831 return upAssignment(variableInfo.index2Variable(0),
832 substitution[0],
833 m,
834 qidMap,
835 dagNodeMap);
836 }
837
838 Vector<DagNode*> args(nrVariables);
839 for (int i = 0; i < nrVariables; ++i)
840 {
841 args[i] = upAssignment(variableInfo.index2Variable(i),
842 substitution[i],
843 m,
844 qidMap,
845 dagNodeMap);
846 }
847 return substitutionSymbol->makeDagNode(args);
848 }
849
850 DagNode*
upUnificationPair(const Vector<DagNode * > & unifier,const NarrowingVariableInfo & variableInfo,const mpz_class & variableIndex,MixfixModule * m)851 MetaLevel::upUnificationPair(const Vector<DagNode*>& unifier,
852 const NarrowingVariableInfo& variableInfo,
853 const mpz_class& variableIndex,
854 MixfixModule* m)
855 {
856 PointerMap qidMap;
857 PointerMap dagNodeMap;
858 Vector<DagNode*> args(2);
859
860 args[0] = upSubstitution(unifier, variableInfo, unifier.size(), m, qidMap, dagNodeMap);
861 args[1] = succSymbol->makeNatDag(variableIndex);
862 return unificationPairSymbol->makeDagNode(args);
863 }
864
865 void
upDisjointSubstitutions(const Vector<DagNode * > & unifier,const NarrowingVariableInfo & variableInfo,MixfixModule * m,PointerMap & qidMap,PointerMap & dagNodeMap,DagNode * & left,DagNode * & right)866 MetaLevel::upDisjointSubstitutions(const Vector<DagNode*>& unifier,
867 const NarrowingVariableInfo& variableInfo,
868 MixfixModule* m,
869 PointerMap& qidMap,
870 PointerMap& dagNodeMap,
871 DagNode*& left,
872 DagNode*& right)
873 {
874 int nrVariables = unifier.size();
875 Vector<DagNode*> leftArgs(0, nrVariables);
876 Vector<DagNode*> rightArgs(0, nrVariables);
877 for (int i = 0; i < nrVariables; i++)
878 {
879 VariableDagNode* variable = variableInfo.index2Variable(i);
880 DagNode* d = upAssignment(variable,
881 unifier[i],
882 m,
883 qidMap,
884 dagNodeMap);
885 if (Token::isFlagged(variable->id()))
886 rightArgs.append(d);
887 else
888 leftArgs.append(d);
889 }
890 int nrLeftArgs = leftArgs.size();
891 if (nrLeftArgs == 0)
892 left = emptySubstitutionSymbol->makeDagNode();
893 else if (nrLeftArgs == 1)
894 left = leftArgs[0];
895 else
896 left = substitutionSymbol->makeDagNode(leftArgs);
897 int nrRightArgs = rightArgs.size();
898 if (nrRightArgs == 0)
899 right = emptySubstitutionSymbol->makeDagNode();
900 else if (nrRightArgs == 1)
901 right = rightArgs[0];
902 else
903 right = substitutionSymbol->makeDagNode(rightArgs);
904 }
905
906 DagNode*
upUnificationTriple(const Vector<DagNode * > & unifier,const NarrowingVariableInfo & variableInfo,const mpz_class & variableIndex,MixfixModule * m)907 MetaLevel::upUnificationTriple(const Vector<DagNode*>& unifier,
908 const NarrowingVariableInfo& variableInfo,
909 const mpz_class& variableIndex,
910 MixfixModule* m)
911 {
912 PointerMap qidMap;
913 PointerMap dagNodeMap;
914 Vector<DagNode*> args(3);
915
916 upDisjointSubstitutions(unifier, variableInfo, m, qidMap, dagNodeMap, args[0], args[1]);
917 args[2] = succSymbol->makeNatDag(variableIndex);
918 return unificationTripleSymbol->makeDagNode(args);
919 }
920
921 DagNode*
upVariant(const Vector<DagNode * > & variant,const NarrowingVariableInfo & variableInfo,const mpz_class & variableIndex,const mpz_class & parentIndex,bool moreInLayer,MixfixModule * m)922 MetaLevel::upVariant(const Vector<DagNode*>& variant,
923 const NarrowingVariableInfo& variableInfo,
924 const mpz_class& variableIndex,
925 const mpz_class& parentIndex,
926 bool moreInLayer,
927 MixfixModule* m)
928 {
929 PointerMap qidMap;
930 PointerMap dagNodeMap;
931 Vector<DagNode*> args(5);
932
933 int nrVariables = variant.size() - 1;
934 args[0] = upDagNode(variant[nrVariables], m, qidMap, dagNodeMap);
935 args[1] = upSubstitution(variant, variableInfo, nrVariables, m, qidMap, dagNodeMap);
936 args[2] = succSymbol->makeNatDag(variableIndex);
937 args[3] = (parentIndex >= 0) ? succSymbol->makeNatDag(parentIndex) :
938 noParentSymbol->makeDagNode();
939 args[4] = upBool(moreInLayer);
940 return variantSymbol->makeDagNode(args);
941 }
942
943 DagNode*
upNoVariant(bool incomplete)944 MetaLevel::upNoVariant(bool incomplete)
945 {
946 return (incomplete ? noVariantIncompleteSymbol : noVariantSymbol)->makeDagNode();
947 }
948
949 DagNode*
upSMT_Number(const mpq_class & value,Symbol * symbol,MixfixModule * m,PointerMap & qidMap)950 MetaLevel::upSMT_Number(const mpq_class& value, Symbol* symbol, MixfixModule* m, PointerMap& qidMap)
951 {
952 Sort* sort = symbol->getRangeSort();
953 int id = m->getSMT_NumberToken(value, sort);
954 return upJoin(id, sort, '.', qidMap);
955 }
956