GCC Code Coverage Report
Directory: . Exec Total Coverage
File: src/theory/arith/nl/nonlinear_extension.cpp Lines: 297 331 89.7 %
Date: 2021-08-20 Branches: 492 973 50.6 %

Line Exec Source
1
/******************************************************************************
2
 * Top contributors (to current version):
3
 *   Andrew Reynolds, Gereon Kremer, Tim King
4
 *
5
 * This file is part of the cvc5 project.
6
 *
7
 * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
8
 * in the top-level source directory and their institutional affiliations.
9
 * All rights reserved.  See the file COPYING in the top-level source
10
 * directory for licensing information.
11
 * ****************************************************************************
12
 *
13
 * [[ Add one-line brief description here ]]
14
 *
15
 * [[ Add lengthier description here ]]
16
 * \todo document this file
17
 */
18
19
#include "theory/arith/nl/nonlinear_extension.h"
20
21
#include "options/arith_options.h"
22
#include "options/smt_options.h"
23
#include "theory/arith/arith_state.h"
24
#include "theory/arith/bound_inference.h"
25
#include "theory/arith/inference_manager.h"
26
#include "theory/arith/nl/nl_lemma_utils.h"
27
#include "theory/arith/theory_arith.h"
28
#include "theory/ext_theory.h"
29
#include "theory/rewriter.h"
30
#include "theory/theory_model.h"
31
#include "util/rational.h"
32
33
using namespace cvc5::kind;
34
35
namespace cvc5 {
36
namespace theory {
37
namespace arith {
38
namespace nl {
39
40
5150
NonlinearExtension::NonlinearExtension(TheoryArith& containing,
41
5150
                                       ArithState& state)
42
    : d_containing(containing),
43
      d_astate(state),
44
5150
      d_im(containing.getInferenceManager()),
45
      d_needsLastCall(false),
46
      d_checkCounter(0),
47
      d_extTheoryCb(state.getEqualityEngine()),
48
      d_extTheory(d_extTheoryCb,
49
                  containing.getSatContext(),
50
                  containing.getUserContext(),
51
5150
                  d_im),
52
      d_model(),
53
5150
      d_trSlv(d_im, d_model, d_astate.getEnv()),
54
5150
      d_extState(d_im, d_model, d_astate.getEnv()),
55
      d_factoringSlv(&d_extState),
56
      d_monomialBoundsSlv(&d_extState),
57
      d_monomialSlv(&d_extState),
58
      d_splitZeroSlv(&d_extState),
59
      d_tangentPlaneSlv(&d_extState),
60
5150
      d_cadSlv(d_astate.getEnv(), d_im, d_model),
61
      d_icpSlv(d_im),
62
      d_iandSlv(d_im, state, d_model),
63
30900
      d_pow2Slv(d_im, state, d_model)
64
{
65
5150
  d_extTheory.addFunctionKind(kind::NONLINEAR_MULT);
66
5150
  d_extTheory.addFunctionKind(kind::EXPONENTIAL);
67
5150
  d_extTheory.addFunctionKind(kind::SINE);
68
5150
  d_extTheory.addFunctionKind(kind::PI);
69
5150
  d_extTheory.addFunctionKind(kind::IAND);
70
5150
  d_extTheory.addFunctionKind(kind::POW2);
71
5150
  d_true = NodeManager::currentNM()->mkConst(true);
72
5150
  d_zero = NodeManager::currentNM()->mkConst(Rational(0));
73
5150
  d_one = NodeManager::currentNM()->mkConst(Rational(1));
74
5150
  d_neg_one = NodeManager::currentNM()->mkConst(Rational(-1));
75
76
5150
  if (d_astate.getEnv().isTheoryProofProducing())
77
  {
78
589
    ProofChecker* pc = d_astate.getEnv().getProofNodeManager()->getChecker();
79
589
    d_proofChecker.registerTo(pc);
80
  }
81
5150
}
82
83
5150
NonlinearExtension::~NonlinearExtension() {}
84
85
378907
void NonlinearExtension::preRegisterTerm(TNode n)
86
{
87
  // register terms with extended theory, to find extended terms that can be
88
  // eliminated by context-depedendent simplification.
89
378907
  d_extTheory.registerTerm(n);
90
378907
}
91
92
void NonlinearExtension::processSideEffect(const NlLemma& se)
93
{
94
  d_trSlv.processSideEffect(se);
95
}
96
97
40720
const Options& NonlinearExtension::options() const
98
{
99
40720
  return d_containing.options();
100
}
101
102
void NonlinearExtension::computeRelevantAssertions(
103
    const std::vector<Node>& assertions, std::vector<Node>& keep)
104
{
105
  Trace("nl-ext-rlv") << "Compute relevant assertions..." << std::endl;
106
  Valuation v = d_containing.getValuation();
107
  for (const Node& a : assertions)
108
  {
109
    if (v.isRelevant(a))
110
    {
111
      keep.push_back(a);
112
    }
113
  }
114
  Trace("nl-ext-rlv") << "...keep " << keep.size() << "/" << assertions.size()
115
                      << " assertions" << std::endl;
116
}
117
118
2987
void NonlinearExtension::getAssertions(std::vector<Node>& assertions)
119
{
120
2987
  Trace("nl-ext-assert-debug") << "Getting assertions..." << std::endl;
121
2987
  bool useRelevance = false;
122
2987
  if (options().arith.nlRlvMode == options::NlRlvMode::INTERLEAVE)
123
  {
124
501
    useRelevance = (d_checkCounter % 2);
125
  }
126
2486
  else if (options().arith.nlRlvMode == options::NlRlvMode::ALWAYS)
127
  {
128
44
    useRelevance = true;
129
  }
130
2987
  Valuation v = d_containing.getValuation();
131
132
5974
  BoundInference bounds;
133
134
5974
  std::unordered_set<Node> init_assertions;
135
136
284108
  for (Theory::assertions_iterator it = d_containing.facts_begin();
137
284108
       it != d_containing.facts_end();
138
       ++it)
139
  {
140
281121
    const Assertion& assertion = *it;
141
562242
    Trace("nl-ext-assert-debug")
142
281121
        << "Loaded " << assertion.d_assertion << " from theory" << std::endl;
143
322162
    Node lit = assertion.d_assertion;
144
281121
    if (useRelevance && !v.isRelevant(lit))
145
    {
146
      // not relevant, skip
147
1714
      continue;
148
    }
149
279407
    if (bounds.add(lit, false))
150
    {
151
238366
      continue;
152
    }
153
41041
    init_assertions.insert(lit);
154
  }
155
156
129497
  for (const auto& vb : bounds.get())
157
  {
158
126510
    const Bounds& b = vb.second;
159
126510
    if (!b.lower_bound.isNull())
160
    {
161
87261
      init_assertions.insert(b.lower_bound);
162
    }
163
126510
    if (!b.upper_bound.isNull())
164
    {
165
71982
      init_assertions.insert(b.upper_bound);
166
    }
167
  }
168
169
  // Try to be "more deterministic" by adding assertions in the order they were
170
  // given
171
284108
  for (auto it = d_containing.facts_begin(); it != d_containing.facts_end();
172
       ++it)
173
  {
174
562242
    Node lit = (*it).d_assertion;
175
281121
    auto iait = init_assertions.find(lit);
176
281121
    if (iait != init_assertions.end())
177
    {
178
170630
      Trace("nl-ext-assert-debug") << "Adding " << lit << std::endl;
179
170630
      assertions.push_back(lit);
180
170630
      init_assertions.erase(iait);
181
    }
182
  }
183
  // Now add left over assertions that have been newly created within this
184
  // function by the code above.
185
5639
  for (const Node& a : init_assertions)
186
  {
187
2652
    Trace("nl-ext-assert-debug") << "Adding " << a << std::endl;
188
2652
    assertions.push_back(a);
189
  }
190
5974
  Trace("nl-ext") << "...keep " << assertions.size() << " / "
191
5974
                  << d_containing.numAssertions() << " assertions."
192
2987
                  << std::endl;
193
2987
}
194
195
2987
std::vector<Node> NonlinearExtension::checkModelEval(
196
    const std::vector<Node>& assertions)
197
{
198
2987
  std::vector<Node> false_asserts;
199
176269
  for (size_t i = 0; i < assertions.size(); ++i)
200
  {
201
346564
    Node lit = assertions[i];
202
346564
    Node atom = lit.getKind() == NOT ? lit[0] : lit;
203
346564
    Node litv = d_model.computeConcreteModelValue(lit);
204
173282
    Trace("nl-ext-mv-assert") << "M[[ " << lit << " ]] -> " << litv;
205
173282
    if (litv != d_true)
206
    {
207
39137
      Trace("nl-ext-mv-assert") << " [model-false]" << std::endl;
208
39137
      false_asserts.push_back(lit);
209
    }
210
    else
211
    {
212
134145
      Trace("nl-ext-mv-assert") << std::endl;
213
    }
214
  }
215
2987
  return false_asserts;
216
}
217
218
265
bool NonlinearExtension::checkModel(const std::vector<Node>& assertions)
219
{
220
265
  Trace("nl-ext-cm") << "--- check-model ---" << std::endl;
221
222
  // get the presubstitution
223
265
  Trace("nl-ext-cm-debug") << "  apply pre-substitution..." << std::endl;
224
  // Notice that we do not consider relevance here, since assertions were
225
  // already filtered based on relevance. It is incorrect to filter based on
226
  // relevance here, since we may have discarded literals that are relevant
227
  // that are entailed based on the techniques in getAssertions.
228
530
  std::vector<Node> passertions = assertions;
229
265
  if (options().arith.nlExt == options::NlExtMode::FULL)
230
  {
231
    // preprocess the assertions with the trancendental solver
232
249
    if (!d_trSlv.preprocessAssertionsCheckModel(passertions))
233
    {
234
      return false;
235
    }
236
  }
237
265
  if (options().arith.nlCad)
238
  {
239
16
    d_cadSlv.constructModelIfAvailable(passertions);
240
  }
241
242
265
  Trace("nl-ext-cm") << "-----" << std::endl;
243
265
  unsigned tdegree = d_trSlv.getTaylorDegree();
244
530
  std::vector<NlLemma> lemmas;
245
265
  bool ret = d_model.checkModel(passertions, tdegree, lemmas);
246
265
  for (const auto& al: lemmas)
247
  {
248
    d_im.addPendingLemma(al);
249
  }
250
265
  return ret;
251
}
252
253
36923
void NonlinearExtension::check(Theory::Effort e)
254
{
255
36923
  d_im.reset();
256
36923
  Trace("nl-ext") << std::endl;
257
36923
  Trace("nl-ext") << "NonlinearExtension::check, effort = " << e << std::endl;
258
36923
  if (e == Theory::EFFORT_FULL)
259
  {
260
33938
    d_needsLastCall = true;
261
33938
    if (options().arith.nlExtRewrites)
262
    {
263
67876
      std::vector<Node> nred;
264
33938
      if (!d_extTheory.doInferences(0, nred))
265
      {
266
66836
        Trace("nl-ext") << "...sent no lemmas, # extf to reduce = "
267
33418
                        << nred.size() << std::endl;
268
33418
        if (nred.empty())
269
        {
270
29959
          d_needsLastCall = false;
271
        }
272
      }
273
      else
274
      {
275
520
        Trace("nl-ext") << "...sent lemmas." << std::endl;
276
      }
277
    }
278
  }
279
  else
280
  {
281
    // If we computed lemmas during collectModelInfo, send them now.
282
2985
    if (d_im.hasPendingLemma())
283
    {
284
2700
      d_im.doPendingFacts();
285
2700
      d_im.doPendingLemmas();
286
2700
      d_im.doPendingPhaseRequirements();
287
2700
      return;
288
    }
289
    // Otherwise, we will answer SAT. The values that we approximated are
290
    // recorded as approximations here.
291
285
    TheoryModel* tm = d_containing.getValuation().getModel();
292
312
    for (std::pair<const Node, std::pair<Node, Node>>& a : d_approximations)
293
    {
294
27
      if (a.second.second.isNull())
295
      {
296
27
        tm->recordApproximation(a.first, a.second.first);
297
      }
298
      else
299
      {
300
        tm->recordApproximation(a.first, a.second.first, a.second.second);
301
      }
302
    }
303
292
    for (const auto& vw : d_witnesses)
304
    {
305
7
      tm->recordApproximation(vw.first, vw.second);
306
    }
307
  }
308
}
309
310
2987
Result::Sat NonlinearExtension::modelBasedRefinement(const std::set<Node>& termSet)
311
{
312
2987
  ++(d_stats.d_mbrRuns);
313
2987
  d_checkCounter++;
314
315
  // get the assertions
316
5974
  std::vector<Node> assertions;
317
2987
  getAssertions(assertions);
318
319
5974
  Trace("nl-ext-mv-assert")
320
2987
      << "Getting model values... check for [model-false]" << std::endl;
321
  // get the assertions that are false in the model
322
5974
  const std::vector<Node> false_asserts = checkModelEval(assertions);
323
2987
  Trace("nl-ext") << "# false asserts = " << false_asserts.size() << std::endl;
324
325
  // get the extended terms belonging to this theory
326
5974
  std::vector<Node> xtsAll;
327
2987
  d_extTheory.getTerms(xtsAll);
328
  // only consider those that are currently relevant based on the current
329
  // assertions, i.e. those contained in termSet
330
5974
  std::vector<Node> xts;
331
24525
  for (const Node& x : xtsAll)
332
  {
333
21538
    if (termSet.find(x) != termSet.end())
334
    {
335
21085
      xts.push_back(x);
336
    }
337
  }
338
339
2987
  if (Trace.isOn("nl-ext-debug"))
340
  {
341
    Trace("nl-ext-debug") << "  processing NonlinearExtension::check : "
342
                          << std::endl;
343
    Trace("nl-ext-debug") << "     " << false_asserts.size()
344
                          << " false assertions" << std::endl;
345
    Trace("nl-ext-debug") << "     " << xts.size()
346
                          << " extended terms: " << std::endl;
347
    Trace("nl-ext-debug") << "       ";
348
    for (unsigned j = 0; j < xts.size(); j++)
349
    {
350
      Trace("nl-ext-debug") << xts[j] << " ";
351
    }
352
    Trace("nl-ext-debug") << std::endl;
353
  }
354
355
  // compute whether shared terms have correct values
356
2987
  unsigned num_shared_wrong_value = 0;
357
5974
  std::vector<Node> shared_term_value_splits;
358
  // must ensure that shared terms are equal to their concrete value
359
2987
  Trace("nl-ext-mv") << "Shared terms : " << std::endl;
360
12595
  for (context::CDList<TNode>::const_iterator its =
361
2987
           d_containing.shared_terms_begin();
362
15582
       its != d_containing.shared_terms_end();
363
       ++its)
364
  {
365
25190
    TNode shared_term = *its;
366
    // compute its value in the model, and its evaluation in the model
367
25190
    Node stv0 = d_model.computeConcreteModelValue(shared_term);
368
25190
    Node stv1 = d_model.computeAbstractModelValue(shared_term);
369
12595
    d_model.printModelValue("nl-ext-mv", shared_term);
370
12595
    if (stv0 != stv1)
371
    {
372
545
      num_shared_wrong_value++;
373
1090
      Trace("nl-ext-mv") << "Bad shared term value : " << shared_term
374
545
                         << std::endl;
375
545
      if (shared_term != stv0)
376
      {
377
        // split on the value, this is non-terminating in general, TODO :
378
        // improve this
379
1058
        Node eq = shared_term.eqNode(stv0);
380
529
        shared_term_value_splits.push_back(eq);
381
      }
382
      else
383
      {
384
        // this can happen for transcendental functions
385
        // the problem is that we cannot evaluate transcendental functions
386
        // (they don't have a rewriter that returns constants)
387
        // thus, the actual value in their model can be themselves, hence we
388
        // have no reference point to rule out the current model.  In this
389
        // case, we may set incomplete below.
390
      }
391
    }
392
  }
393
5974
  Trace("nl-ext-debug") << "     " << num_shared_wrong_value
394
2987
                        << " shared terms with wrong model value." << std::endl;
395
  bool needsRecheck;
396
315
  do
397
  {
398
3003
    d_model.resetCheck();
399
3003
    needsRecheck = false;
400
    // complete_status:
401
    //   1 : we may answer SAT, -1 : we may not answer SAT, 0 : unknown
402
3003
    int complete_status = 1;
403
    // We require a check either if an assertion is false or a shared term has
404
    // a wrong value
405
3003
    if (!false_asserts.empty() || num_shared_wrong_value > 0)
406
    {
407
2786
      complete_status = num_shared_wrong_value > 0 ? -1 : 0;
408
2786
      runStrategy(Theory::Effort::EFFORT_FULL, assertions, false_asserts, xts);
409
2786
      if (d_im.hasSentLemma() || d_im.hasPendingLemma())
410
      {
411
2503
        d_im.clearWaitingLemmas();
412
5207
        return Result::Sat::UNSAT;
413
      }
414
    }
415
1000
    Trace("nl-ext") << "Finished check with status : " << complete_status
416
500
                    << std::endl;
417
418
    // if we did not add a lemma during check and there is a chance for SAT
419
500
    if (complete_status == 0)
420
    {
421
530
      Trace("nl-ext")
422
265
          << "Check model based on bounds for irrational-valued functions..."
423
265
          << std::endl;
424
      // check the model based on simple solving of equalities and using
425
      // error bounds on the Taylor approximation of transcendental functions.
426
265
      if (checkModel(assertions))
427
      {
428
66
        complete_status = 1;
429
      }
430
265
      if (d_im.hasUsed())
431
      {
432
        d_im.clearWaitingLemmas();
433
        return Result::Sat::UNSAT;
434
      }
435
    }
436
437
    // if we have not concluded SAT
438
500
    if (complete_status != 1)
439
    {
440
      // flush the waiting lemmas
441
217
      if (d_im.hasWaitingLemma())
442
      {
443
183
        std::size_t count = d_im.numWaitingLemmas();
444
183
        d_im.flushWaitingLemmas();
445
366
        Trace("nl-ext") << "...added " << count << " waiting lemmas."
446
183
                        << std::endl;
447
183
        return Result::Sat::UNSAT;
448
      }
449
      // resort to splitting on shared terms with their model value
450
      // if we did not add any lemmas
451
34
      if (num_shared_wrong_value > 0)
452
      {
453
18
        complete_status = -1;
454
18
        if (!shared_term_value_splits.empty())
455
        {
456
88
          for (const Node& eq : shared_term_value_splits)
457
          {
458
144
            Node req = Rewriter::rewrite(eq);
459
144
            Node literal = d_containing.getValuation().ensureLiteral(req);
460
72
            d_containing.getOutputChannel().requirePhase(literal, true);
461
72
            Trace("nl-ext-debug") << "Split on : " << literal << std::endl;
462
144
            Node split = literal.orNode(literal.negate());
463
72
            d_im.addPendingLemma(split,
464
                                 InferenceId::ARITH_NL_SHARED_TERM_VALUE_SPLIT,
465
                                 nullptr,
466
                                 true);
467
          }
468
16
          if (d_im.hasWaitingLemma())
469
          {
470
14
            d_im.flushWaitingLemmas();
471
28
            Trace("nl-ext") << "...added " << d_im.numPendingLemmas()
472
14
                            << " shared term value split lemmas." << std::endl;
473
14
            return Result::Sat::UNSAT;
474
          }
475
        }
476
        else
477
        {
478
          // this can happen if we are trying to do theory combination with
479
          // trancendental functions
480
          // since their model value cannot even be computed exactly
481
        }
482
      }
483
484
      // we are incomplete
485
40
      if (options().arith.nlExt == options::NlExtMode::FULL
486
20
          && options().arith.nlExtIncPrecision && d_model.usedApproximate())
487
      {
488
16
        d_trSlv.incrementTaylorDegree();
489
16
        needsRecheck = true;
490
        // increase precision for PI?
491
        // Difficult since Taylor series is very slow to converge
492
32
        Trace("nl-ext") << "...increment Taylor degree to "
493
16
                        << d_trSlv.getTaylorDegree() << std::endl;
494
      }
495
      else
496
      {
497
8
        Trace("nl-ext") << "...failed to send lemma in "
498
4
                           "NonLinearExtension, set incomplete"
499
4
                        << std::endl;
500
4
        d_containing.getOutputChannel().setIncomplete(IncompleteId::ARITH_NL);
501
4
        return Result::Sat::SAT_UNKNOWN;
502
      }
503
    }
504
299
    d_im.clearWaitingLemmas();
505
  } while (needsRecheck);
506
507
  // did not add lemmas
508
283
  return Result::Sat::SAT;
509
}
510
511
8911
void NonlinearExtension::interceptModel(std::map<Node, Node>& arithModel,
512
                                        const std::set<Node>& termSet)
513
{
514
8911
  if (!needsCheckLastEffort())
515
  {
516
    // no non-linear constraints, we are done
517
5924
    return;
518
  }
519
2987
  Trace("nl-ext") << "NonlinearExtension::interceptModel begin" << std::endl;
520
2987
  d_model.reset(d_containing.getValuation().getModel(), arithModel);
521
  // run a last call effort check
522
2987
  Trace("nl-ext") << "interceptModel: do model-based refinement" << std::endl;
523
2987
  Result::Sat res = modelBasedRefinement(termSet);
524
2987
  if (res == Result::Sat::SAT)
525
  {
526
283
    Trace("nl-ext") << "interceptModel: do model repair" << std::endl;
527
283
    d_approximations.clear();
528
283
    d_witnesses.clear();
529
    // modify the model values
530
566
    d_model.getModelValueRepair(arithModel,
531
                                d_approximations,
532
                                d_witnesses,
533
283
                                options().smt.modelWitnessValue);
534
  }
535
}
536
537
6408
void NonlinearExtension::presolve()
538
{
539
6408
  Trace("nl-ext") << "NonlinearExtension::presolve" << std::endl;
540
6408
}
541
542
2786
void NonlinearExtension::runStrategy(Theory::Effort effort,
543
                                     const std::vector<Node>& assertions,
544
                                     const std::vector<Node>& false_asserts,
545
                                     const std::vector<Node>& xts)
546
{
547
2786
  ++(d_stats.d_checkRuns);
548
549
2786
  if (Trace.isOn("nl-strategy"))
550
  {
551
    for (const auto& a : assertions)
552
    {
553
      Trace("nl-strategy") << "Input assertion: " << a << std::endl;
554
    }
555
  }
556
2786
  if (!d_strategy.isStrategyInit())
557
  {
558
458
    d_strategy.initializeStrategy(options());
559
  }
560
561
2786
  auto steps = d_strategy.getStrategy();
562
2786
  bool stop = false;
563
99122
  while (!stop && steps.hasNext())
564
  {
565
48168
    InferStep step = steps.next();
566
48168
    Trace("nl-strategy") << "Step " << step << std::endl;
567
48168
    switch (step)
568
    {
569
21627
      case InferStep::BREAK: stop = d_im.hasPendingLemma(); break;
570
369
      case InferStep::FLUSH_WAITING_LEMMAS: d_im.flushWaitingLemmas(); break;
571
46
      case InferStep::CAD_FULL: d_cadSlv.checkFull(); break;
572
46
      case InferStep::CAD_INIT: d_cadSlv.initLastCall(assertions); break;
573
276
      case InferStep::NL_FACTORING:
574
276
        d_factoringSlv.check(assertions, false_asserts);
575
276
        break;
576
2456
      case InferStep::IAND_INIT:
577
2456
        d_iandSlv.initLastCall(assertions, false_asserts, xts);
578
2456
        break;
579
297
      case InferStep::IAND_FULL: d_iandSlv.checkFullRefine(); break;
580
2456
      case InferStep::IAND_INITIAL: d_iandSlv.checkInitialRefine(); break;
581
2389
      case InferStep::POW2_INIT:
582
2389
        d_pow2Slv.initLastCall(assertions, false_asserts, xts);
583
2389
        break;
584
297
      case InferStep::POW2_FULL: d_pow2Slv.checkFullRefine(); break;
585
2389
      case InferStep::POW2_INITIAL: d_pow2Slv.checkInitialRefine(); break;
586
32
      case InferStep::ICP:
587
32
        d_icpSlv.reset(assertions);
588
32
        d_icpSlv.check();
589
32
        break;
590
2775
      case InferStep::NL_INIT:
591
2775
        d_extState.init(xts);
592
2775
        d_monomialBoundsSlv.init();
593
2775
        d_monomialSlv.init(xts);
594
2775
        break;
595
524
      case InferStep::NL_MONOMIAL_INFER_BOUNDS:
596
524
        d_monomialBoundsSlv.checkBounds(assertions, false_asserts);
597
524
        break;
598
1526
      case InferStep::NL_MONOMIAL_MAGNITUDE0:
599
1526
        d_monomialSlv.checkMagnitude(0);
600
1526
        break;
601
1024
      case InferStep::NL_MONOMIAL_MAGNITUDE1:
602
1024
        d_monomialSlv.checkMagnitude(1);
603
1024
        break;
604
751
      case InferStep::NL_MONOMIAL_MAGNITUDE2:
605
751
        d_monomialSlv.checkMagnitude(2);
606
751
        break;
607
2362
      case InferStep::NL_MONOMIAL_SIGN: d_monomialSlv.checkSign(); break;
608
      case InferStep::NL_RESOLUTION_BOUNDS:
609
        d_monomialBoundsSlv.checkResBounds();
610
        break;
611
      case InferStep::NL_SPLIT_ZERO: d_splitZeroSlv.check(); break;
612
      case InferStep::NL_TANGENT_PLANES: d_tangentPlaneSlv.check(false); break;
613
25
      case InferStep::NL_TANGENT_PLANES_WAITING:
614
25
        d_tangentPlaneSlv.check(true);
615
25
        break;
616
2682
      case InferStep::TRANS_INIT:
617
2682
        d_trSlv.initLastCall(xts);
618
2682
        break;
619
2515
      case InferStep::TRANS_INITIAL:
620
2515
        d_trSlv.checkTranscendentalInitialRefine();
621
2515
        break;
622
1055
      case InferStep::TRANS_MONOTONIC:
623
1055
        d_trSlv.checkTranscendentalMonotonic();
624
1055
        break;
625
249
      case InferStep::TRANS_TANGENT_PLANES:
626
249
        d_trSlv.checkTranscendentalTangentPlanes();
627
249
        break;
628
    }
629
  }
630
631
2786
  Trace("nl-ext") << "finished strategy" << std::endl;
632
5572
  Trace("nl-ext") << "  ...finished with " << d_im.numWaitingLemmas()
633
2786
                  << " waiting lemmas." << std::endl;
634
5572
  Trace("nl-ext") << "  ...finished with " << d_im.numPendingLemmas()
635
2786
                  << " pending lemmas." << std::endl;
636
2786
}
637
638
}  // namespace nl
639
}  // namespace arith
640
}  // namespace theory
641
29358
}  // namespace cvc5