Refactor java package name from cvc5 to io.github.cvc5.api (#7340)
authormudathirmahgoub <mudathirmahgoub@gmail.com>
Fri, 22 Oct 2021 23:00:06 +0000 (18:00 -0500)
committerGitHub <noreply@github.com>
Fri, 22 Oct 2021 23:00:06 +0000 (23:00 +0000)
This PR refactors java package name from cvc5 to io.github.cvc5.api.
It also refactor the names of cpp and java files.

117 files changed:
docs/api/java/CMakeLists.txt
examples/api/java/BitVectors.java
examples/api/java/BitVectorsAndArrays.java
examples/api/java/Combination.java
examples/api/java/Datatypes.java
examples/api/java/Exceptions.java
examples/api/java/Extract.java
examples/api/java/FloatingPointArith.java
examples/api/java/HelloWorld.java
examples/api/java/LinearArith.java
examples/api/java/QuickStart.java
examples/api/java/Relations.java
examples/api/java/Sequences.java
examples/api/java/Sets.java
examples/api/java/Statistics.java
examples/api/java/Strings.java
examples/api/java/SygusFun.java
examples/api/java/SygusGrammar.java
examples/api/java/SygusInv.java
examples/api/java/Transcendentals.java
examples/api/java/UnsatCores.java
src/api/java/CMakeLists.txt
src/api/java/cvc5/AbstractPointer.java [deleted file]
src/api/java/cvc5/CVC5ApiException.java [deleted file]
src/api/java/cvc5/CVC5ApiOptionException.java [deleted file]
src/api/java/cvc5/CVC5ApiRecoverableException.java [deleted file]
src/api/java/cvc5/Datatype.java [deleted file]
src/api/java/cvc5/DatatypeConstructor.java [deleted file]
src/api/java/cvc5/DatatypeConstructorDecl.java [deleted file]
src/api/java/cvc5/DatatypeDecl.java [deleted file]
src/api/java/cvc5/DatatypeSelector.java [deleted file]
src/api/java/cvc5/Grammar.java [deleted file]
src/api/java/cvc5/IPointer.java [deleted file]
src/api/java/cvc5/Op.java [deleted file]
src/api/java/cvc5/OptionInfo.java [deleted file]
src/api/java/cvc5/Pair.java [deleted file]
src/api/java/cvc5/Result.java [deleted file]
src/api/java/cvc5/RoundingMode.java [deleted file]
src/api/java/cvc5/Solver.java [deleted file]
src/api/java/cvc5/Sort.java [deleted file]
src/api/java/cvc5/Stat.java [deleted file]
src/api/java/cvc5/Statistics.java [deleted file]
src/api/java/cvc5/Term.java [deleted file]
src/api/java/cvc5/Triplet.java [deleted file]
src/api/java/cvc5/Utils.java [deleted file]
src/api/java/genkinds.py.in
src/api/java/io/github/cvc5/api/AbstractPointer.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/CVC5ApiException.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/CVC5ApiOptionException.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/CVC5ApiRecoverableException.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Datatype.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/DatatypeConstructor.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/DatatypeConstructorDecl.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/DatatypeDecl.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/DatatypeSelector.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Grammar.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/IPointer.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Op.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/OptionInfo.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Pair.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Result.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/RoundingMode.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Solver.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Sort.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Stat.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Statistics.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Term.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Triplet.java [new file with mode: 0644]
src/api/java/io/github/cvc5/api/Utils.java [new file with mode: 0644]
src/api/java/jni/api_utilities.cpp [new file with mode: 0644]
src/api/java/jni/api_utilities.h [new file with mode: 0644]
src/api/java/jni/cvc5JavaApi.cpp [deleted file]
src/api/java/jni/cvc5JavaApi.h [deleted file]
src/api/java/jni/cvc5_Datatype.cpp [deleted file]
src/api/java/jni/cvc5_DatatypeConstructor.cpp [deleted file]
src/api/java/jni/cvc5_DatatypeConstructorDecl.cpp [deleted file]
src/api/java/jni/cvc5_DatatypeDecl.cpp [deleted file]
src/api/java/jni/cvc5_DatatypeSelector.cpp [deleted file]
src/api/java/jni/cvc5_Grammar.cpp [deleted file]
src/api/java/jni/cvc5_Op.cpp [deleted file]
src/api/java/jni/cvc5_OptionInfo.cpp [deleted file]
src/api/java/jni/cvc5_Result.cpp [deleted file]
src/api/java/jni/cvc5_Solver.cpp [deleted file]
src/api/java/jni/cvc5_Sort.cpp [deleted file]
src/api/java/jni/cvc5_Stat.cpp [deleted file]
src/api/java/jni/cvc5_Statistics.cpp [deleted file]
src/api/java/jni/cvc5_Term.cpp [deleted file]
src/api/java/jni/datatype.cpp [new file with mode: 0644]
src/api/java/jni/datatype_constructor.cpp [new file with mode: 0644]
src/api/java/jni/datatype_constructor_decl.cpp [new file with mode: 0644]
src/api/java/jni/datatype_decl.cpp [new file with mode: 0644]
src/api/java/jni/datatype_selector.cpp [new file with mode: 0644]
src/api/java/jni/grammar.cpp [new file with mode: 0644]
src/api/java/jni/op.cpp [new file with mode: 0644]
src/api/java/jni/option_Info.cpp [new file with mode: 0644]
src/api/java/jni/option_info.cpp [new file with mode: 0644]
src/api/java/jni/result.cpp [new file with mode: 0644]
src/api/java/jni/solver.cpp [new file with mode: 0644]
src/api/java/jni/sort.cpp [new file with mode: 0644]
src/api/java/jni/stat.cpp [new file with mode: 0644]
src/api/java/jni/statistics.cpp [new file with mode: 0644]
src/api/java/jni/term.cpp [new file with mode: 0644]
test/unit/api/java/CMakeLists.txt
test/unit/api/java/DatatypeTest.java [new file with mode: 0644]
test/unit/api/java/GrammarTest.java [new file with mode: 0644]
test/unit/api/java/OpTest.java [new file with mode: 0644]
test/unit/api/java/ResultTest.java [new file with mode: 0644]
test/unit/api/java/SolverTest.java [new file with mode: 0644]
test/unit/api/java/SortTest.java [new file with mode: 0644]
test/unit/api/java/TermTest.java [new file with mode: 0644]
test/unit/api/java/cvc5/DatatypeTest.java [deleted file]
test/unit/api/java/cvc5/GrammarTest.java [deleted file]
test/unit/api/java/cvc5/OpTest.java [deleted file]
test/unit/api/java/cvc5/ResultTest.java [deleted file]
test/unit/api/java/cvc5/SolverTest.java [deleted file]
test/unit/api/java/cvc5/SortTest.java [deleted file]
test/unit/api/java/cvc5/TermTest.java [deleted file]

index 20a5d91a3a83d5a717da8a31b25e72e952121103..7c897a3549eecc10cb0983bca800cfd0dcca86fc 100644 (file)
@@ -28,7 +28,7 @@ if(BUILD_BINDINGS_JAVA)
   add_custom_command(
     OUTPUT "${JAVADOC_INDEX_FILE}"
     COMMAND 
-      ${Java_JAVADOC_EXECUTABLE} cvc5
+      ${Java_JAVADOC_EXECUTABLE} io.github.cvc5.api
       -sourcepath ${CMAKE_SOURCE_DIR}/src/api/java/
       -d ${JAVADOC_OUTPUT_DIR}
       -cp ${CMAKE_BINARY_DIR}/src/api/java/cvc5.jar
index 181c16614faf894772e75bf22a33d3912ad602fa..6209cf9dd0eeb3fa1eb25237418f6ccea7ed1d57 100644 (file)
@@ -15,7 +15,7 @@
  *
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.util.*;
 
 public class BitVectors
index 3e22604dd064568beb6d72bf8903c8aa0fa52206..07b9781d2845049c77f76b9d7b061ad4b66ac415 100644 (file)
@@ -15,7 +15,7 @@
  *
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.util.*;
 
 public class BitVectorsAndArrays
index d25ea849ef673e053412f3afc38478fd9d5ecfd8..66cd30b2b6f26078d171ecd7094537a24d02a152 100644 (file)
@@ -17,7 +17,7 @@
  * The model is displayed using getValue().
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.util.Iterator;
 
 public class Combination
index b230affd504b47aeda985dfa8b527e6e63128455..85f8780980aec8041265074851cbb99137538543 100644 (file)
@@ -13,7 +13,7 @@
  * An example of using inductive datatypes in cvc5.
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.util.Iterator;
 
 public class Datatypes
index bf87fc6bee3b35675e524aad0a69360befcddf14..2d62a7570869aa791590a23d34ef69a30e24c2c3 100644 (file)
@@ -15,7 +15,7 @@
  * A simple demonstration of catching CVC4 execptions via the Java API.
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class Exceptions
 {
index d86b7b1ef3007815bdecbcd6b5f7f39bb33ea06f..0d8d6c2b2e4757afa6671dae9168157a2cfa9462 100644 (file)
@@ -15,7 +15,7 @@
  *
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class Extract
 {
index dda5bbcd09298518f51c9b091098a97a34a98da7..88e24cbab081472dd2fd6d39cb07fdce4f774e3d 100644 (file)
@@ -18,9 +18,9 @@
  * an IEEE 754-2008 bit-vector to a floating-point number.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class FloatingPointArith
 {
index 1013c0a9e75e5bd7c84a186b97e1ed9789b0829b..966bfb3292b29745b62c61b170a4568fff891a2a 100644 (file)
@@ -13,7 +13,7 @@
  * A very simple CVC5 tutorial example.
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class HelloWorld
 {
index 0c728894a7079ac0c3019e6b87b99e06b7cb934f..2e67d526fc7e582158b8a21ad516fe67fd0d52a3 100644 (file)
@@ -14,7 +14,7 @@
  * the push pop of cvc5. This also gives an example option.
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 public class LinearArith
 {
   public static void main(String args[]) throws CVC5ApiException
index 4e1798d39afdd20fab08916fe2de07b84cc55d4f..73bddb083141f8ba3eab993b92d50c002f775648 100644 (file)
@@ -14,7 +14,7 @@
  *
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.math.BigInteger;
 import java.util.ArrayList;
 import java.util.Arrays;
index cfcbb3b8e4421fb545819d8e056e4f4b0fceaea5..f6454c812fd41e58cb0b6ba51624846baf90f1dc 100644 (file)
@@ -13,9 +13,9 @@
  * A simple demonstration of reasoning about relations with CVC4 via Java API.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 /*
 This file uses the API to make a sat call equivalent to the following benchmark:
index 8d327fb2b36fc9000d51075c33ea86a4f6d31979..d1bb0440d2a101f32d39f39f66088b9b82b6f167 100644 (file)
@@ -13,9 +13,9 @@
  * A simple demonstration of reasoning about sequences with cvc5 via C++ API.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class Sequences
 {
index 38f7d194d9b9347da229f32ed24872b612ee6242..602014c96455d66eb42e6204a3042667cf0caf11 100644 (file)
@@ -13,9 +13,9 @@
  * A simple demonstration of reasoning about sets with cvc5.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class Sets
 {
index c5aad055849b46aff3e35db4c14aa1c67a78384e..e524eb3e34c9383973c3a24b600514e2e159a77e 100644 (file)
@@ -13,9 +13,9 @@
  * An example of accessing CVC4's statistics using the Java API.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.util.List;
 import java.util.Map;
 
@@ -26,7 +26,7 @@ public class Statistics
     Solver solver = getSolver();
     // Get the statistics from the `Solver` and iterate over them. The
     // `Statistics` class implements the `Iterable<Pair<String, Stat>>` interface.
-    cvc5.Statistics stats = solver.getStatistics();
+    io.github.cvc5.api.Statistics stats = solver.getStatistics();
     // short version
     System.out.println("Short version:");
     System.out.println(stats);
index e023459fa72b840fa5afeb5ee1d883d805c4cf20..6cc1521590014f9209b021c06efc96c35a5766c6 100644 (file)
@@ -13,9 +13,9 @@
  * A simple demonstration of reasoning about strings with cvc5 via C++ API.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class Strings
 {
index 1a53a0dd19220bdf83739fe14eee1d564f7c5fed..8b96dff50eac0cb128bcd0154a60288e45288e1e 100644 (file)
@@ -48,9 +48,9 @@
  * )
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class SygusFun
 {
index b39094ae51730eb666bfb07616284d1404c048db..fb079d49f91a588d39c231982a23841ece507da2 100644 (file)
@@ -45,9 +45,9 @@
  * )
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class SygusGrammar
 {
index 47d6797ba306094e9a8e2ba60612a304b05569cb..6c66c910be6570c915b72b337ae927f2b165f47d 100644 (file)
@@ -36,9 +36,9 @@
  * )
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class SygusInv
 {
index 5e8c26820dae5c2fb7095928494e5a9c3d318a0e..026f9b826911ea9e4563968da23e04ebe58c2d06 100644 (file)
@@ -13,9 +13,9 @@
  * A simple demonstration of the transcendental extension.
  */
 
-import static cvc5.Kind.*;
+import static io.github.cvc5.api.Kind.*;
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 
 public class Transcendentals
 {
index 2f83ddc9cfd6f03fec2458cef3a9a8d5dc7d3dab..cefa9029034b1d3082dab719b7fdae926294085b 100644 (file)
@@ -13,7 +13,7 @@
  * An example of interacting with unsat cores using CVC4's Java API.
  */
 
-import cvc5.*;
+import io.github.cvc5.api.*;
 import java.util.Arrays;
 
 public class UnsatCores
index df35390ea32605aa295679f0bf9c1222f31872da..5f522f4d10703da74c516d50166e90ca44964df7 100644 (file)
 ##
 
 # create directories
-file(MAKE_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/cvc5")
+file(MAKE_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/io/github/cvc5/api")
 set(JNI_DIR "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/jni")
 file(MAKE_DIRECTORY ${JNI_DIR})
 
-# Generate cvc5/Kind.java
+# Generate Kind.java
 configure_file(genkinds.py.in genkinds.py)
 
 set(JAVA_KIND_FILE
-  "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/cvc5/Kind.java"
+  "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/io/github/cvc5/api/Kind.java"
 )
 
 add_custom_command(
@@ -34,7 +34,7 @@ add_custom_command(
     "${PYTHON_EXECUTABLE}"
     "${CMAKE_CURRENT_BINARY_DIR}/genkinds.py"
     --kinds-header "${PROJECT_SOURCE_DIR}/src/api/cpp/cvc5_kind.h"
-    --kinds-file-prefix "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/cvc5/Kind"
+    --kinds-file-prefix "${CMAKE_CURRENT_BINARY_DIR}/src/api/java/io/github/cvc5/api/Kind"
   DEPENDS
     "${CMAKE_CURRENT_BINARY_DIR}/genkinds.py"
     "${PROJECT_SOURCE_DIR}/src/api/cpp/cvc5_kind.h"
@@ -48,29 +48,29 @@ include(UseJava)
 
 # specify java source files
 set(JAVA_FILES
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/AbstractPointer.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/CVC5ApiException.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/CVC5ApiOptionException.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/CVC5ApiRecoverableException.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Datatype.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/DatatypeConstructor.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/DatatypeConstructorDecl.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/DatatypeDecl.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/DatatypeSelector.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Grammar.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/IPointer.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Op.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/OptionInfo.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Pair.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Result.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/RoundingMode.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Solver.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Sort.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Stat.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Statistics.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Term.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Triplet.java
-  ${CMAKE_CURRENT_LIST_DIR}/cvc5/Utils.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/AbstractPointer.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/CVC5ApiException.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/CVC5ApiOptionException.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/CVC5ApiRecoverableException.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Datatype.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/DatatypeConstructor.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/DatatypeConstructorDecl.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/DatatypeDecl.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/DatatypeSelector.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Grammar.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/IPointer.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Op.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/OptionInfo.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Pair.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Result.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/RoundingMode.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Solver.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Sort.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Stat.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Statistics.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Term.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Triplet.java
+  ${CMAKE_CURRENT_LIST_DIR}/io/github/cvc5/api/Utils.java
   ${JAVA_KIND_FILE}
 )
 
@@ -110,21 +110,21 @@ message(STATUS "JAVA_INCLUDE_PATH2   : ${JAVA_INCLUDE_PATH2}")
 message(STATUS "JAVA_AWT_INCLUDE_PATH: ${JAVA_AWT_INCLUDE_PATH}")
 
 add_library(cvc5jni SHARED
-  jni/cvc5_Datatype.cpp
-  jni/cvc5_DatatypeConstructor.cpp
-  jni/cvc5_DatatypeConstructorDecl.cpp
-  jni/cvc5_DatatypeDecl.cpp
-  jni/cvc5_DatatypeSelector.cpp
-  jni/cvc5_Grammar.cpp
-  jni/cvc5_Op.cpp
-  jni/cvc5_OptionInfo.cpp
-  jni/cvc5_Result.cpp
-  jni/cvc5_Solver.cpp
-  jni/cvc5_Sort.cpp
-  jni/cvc5_Stat.cpp
-  jni/cvc5_Statistics.cpp
-  jni/cvc5_Term.cpp
-  jni/cvc5JavaApi.cpp)
+  jni/api_utilities.cpp
+  jni/datatype.cpp
+  jni/datatype_constructor.cpp
+  jni/datatype_constructor_decl.cpp
+  jni/datatype_decl.cpp
+  jni/datatype_selector.cpp
+  jni/grammar.cpp
+  jni/op.cpp
+  jni/option_info.cpp
+  jni/result.cpp
+  jni/solver.cpp
+  jni/sort.cpp
+  jni/stat.cpp
+  jni/statistics.cpp
+  jni/term.cpp)
 
 add_dependencies(cvc5jni generate-jni-headers)
 
diff --git a/src/api/java/cvc5/AbstractPointer.java b/src/api/java/cvc5/AbstractPointer.java
deleted file mode 100644 (file)
index 8006b67..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-abstract class AbstractPointer implements IPointer
-{
-  protected final Solver solver;
-  protected final long pointer;
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  public Solver getSolver()
-  {
-    return solver;
-  }
-
-  @Override public String toString()
-  {
-    return toString(pointer);
-  }
-
-  abstract protected String toString(long pointer);
-
-  AbstractPointer(Solver solver, long pointer)
-  {
-    this.solver = solver;
-    this.pointer = pointer;
-  }
-}
diff --git a/src/api/java/cvc5/CVC5ApiException.java b/src/api/java/cvc5/CVC5ApiException.java
deleted file mode 100644 (file)
index 8b8b611..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class CVC5ApiException extends Exception
-{
-  public CVC5ApiException(String message)
-  {
-    super(message);
-  }
-}
diff --git a/src/api/java/cvc5/CVC5ApiOptionException.java b/src/api/java/cvc5/CVC5ApiOptionException.java
deleted file mode 100644 (file)
index e792091..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Gereon Kremer, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class CVC5ApiOptionException extends CVC5ApiRecoverableException
-{
-  public CVC5ApiOptionException(String message)
-  {
-    super(message);
-  }
-}
diff --git a/src/api/java/cvc5/CVC5ApiRecoverableException.java b/src/api/java/cvc5/CVC5ApiRecoverableException.java
deleted file mode 100644 (file)
index 035a79a..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class CVC5ApiRecoverableException extends CVC5ApiException
-{
-  public CVC5ApiRecoverableException(String message)
-  {
-    super(message);
-  }
-}
diff --git a/src/api/java/cvc5/Datatype.java b/src/api/java/cvc5/Datatype.java
deleted file mode 100644 (file)
index 42e0628..0000000
+++ /dev/null
@@ -1,233 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.util.Iterator;
-import java.util.NoSuchElementException;
-
-public class Datatype extends AbstractPointer implements Iterable<DatatypeConstructor>
-{
-  // region construction and destruction
-  Datatype(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * Get the datatype constructor at a given index.
-   * @param idx the index of the datatype constructor to return
-   * @return the datatype constructor with the given index
-   */
-  public DatatypeConstructor getConstructor(int idx)
-  {
-    long constructorPointer = getConstructor(pointer, idx);
-    return new DatatypeConstructor(solver, constructorPointer);
-  }
-
-  private native long getConstructor(long pointer, int index);
-
-  /**
-   * Get the datatype constructor with the given name.
-   * This is a linear search through the constructors, so in case of multiple,
-   * similarly-named constructors, the first is returned.
-   * @param name the name of the datatype constructor
-   * @return the datatype constructor with the given name
-   */
-  public DatatypeConstructor getConstructor(String name)
-  {
-    long constructorPointer = getConstructor(pointer, name);
-    return new DatatypeConstructor(solver, constructorPointer);
-  }
-
-  private native long getConstructor(long pointer, String name);
-
-  /**
-   * Get a term representing the datatype constructor with the given name.
-   * This is a linear search through the constructors, so in case of multiple,
-   * similarly-named constructors, the
-   * first is returned.
-   */
-  public Term getConstructorTerm(String name)
-  {
-    long termPointer = getConstructorTerm(pointer, name);
-    return new Term(solver, termPointer);
-  }
-
-  private native long getConstructorTerm(long pointer, String name);
-
-  /**
-   * Get the datatype constructor with the given name.
-   * This is a linear search through the constructors and their selectors, so
-   * in case of multiple, similarly-named selectors, the first is returned.
-   * @param name the name of the datatype selector
-   * @return the datatype selector with the given name
-   */
-  public DatatypeSelector getSelector(String name)
-  {
-    long selectorPointer = getSelector(pointer, name);
-    return new DatatypeSelector(solver, selectorPointer);
-  }
-
-  private native long getSelector(long pointer, String name);
-
-  /** @return the name of this Datatype. */
-  public String getName()
-  {
-    return getName(pointer);
-  }
-
-  private native String getName(long pointer);
-
-  /** @return the number of constructors for this Datatype. */
-  public int getNumConstructors()
-  {
-    return getNumConstructors(pointer);
-  }
-
-  private native int getNumConstructors(long pointer);
-
-  /** @return true if this datatype is parametric */
-  public boolean isParametric()
-  {
-    return isParametric(pointer);
-  }
-
-  private native boolean isParametric(long pointer);
-
-  /** @return true if this datatype corresponds to a co-datatype */
-  public boolean isCodatatype()
-  {
-    return isCodatatype(pointer);
-  }
-
-  private native boolean isCodatatype(long pointer);
-
-  /** @return true if this datatype corresponds to a tuple */
-  public boolean isTuple()
-  {
-    return isTuple(pointer);
-  }
-
-  private native boolean isTuple(long pointer);
-
-  /** @return true if this datatype corresponds to a record */
-  public boolean isRecord()
-  {
-    return isRecord(pointer);
-  }
-
-  private native boolean isRecord(long pointer);
-
-  /** @return true if this datatype is finite */
-  public boolean isFinite()
-  {
-    return isFinite(pointer);
-  }
-
-  private native boolean isFinite(long pointer);
-
-  /**
-   * Is this datatype well-founded? If this datatype is not a codatatype,
-   * this returns false if there are no values of this datatype that are of
-   * finite size.
-   *
-   * @return true if this datatype is well-founded
-   */
-  public boolean isWellFounded()
-  {
-    return isWellFounded(pointer);
-  }
-
-  private native boolean isWellFounded(long pointer);
-
-  /**
-   * Does this datatype have nested recursion? This method returns false if a
-   * value of this datatype includes a subterm of its type that is nested
-   * beneath a non-datatype type constructor. For example, a datatype
-   * T containing a constructor having a selector with range type (Set T) has
-   * nested recursion.
-   *
-   * @return true if this datatype has nested recursion
-   */
-  public boolean hasNestedRecursion()
-  {
-    return hasNestedRecursion(pointer);
-  }
-
-  private native boolean hasNestedRecursion(long pointer);
-
-  /**
-   * @return true if this Datatype is a null object
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * @return a string representation of this datatype
-   */
-  protected native String toString(long pointer);
-
-  public class ConstIterator implements Iterator<DatatypeConstructor>
-  {
-    private int currentIndex;
-    private int size;
-
-    public ConstIterator()
-    {
-      currentIndex = -1;
-      size = getNumConstructors();
-    }
-
-    @Override public boolean hasNext()
-    {
-      return currentIndex < size - 1;
-    }
-
-    @Override public DatatypeConstructor next()
-    {
-      if (currentIndex >= size - 1)
-      {
-        throw new NoSuchElementException();
-      }
-      currentIndex++;
-
-      return getConstructor(currentIndex);
-    }
-  }
-
-  @Override public Iterator<DatatypeConstructor> iterator()
-  {
-    return new ConstIterator();
-  }
-}
diff --git a/src/api/java/cvc5/DatatypeConstructor.java b/src/api/java/cvc5/DatatypeConstructor.java
deleted file mode 100644 (file)
index 7c0ee21..0000000
+++ /dev/null
@@ -1,197 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.util.Iterator;
-import java.util.NoSuchElementException;
-
-public class DatatypeConstructor extends AbstractPointer implements Iterable<DatatypeSelector>
-{
-  // region construction and destruction
-  DatatypeConstructor(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /** @return the name of this Datatype constructor. */
-  public String getName()
-  {
-    return getName(pointer);
-  }
-
-  private native String getName(long pointer);
-
-  /**
-   * Get the constructor operator of this datatype constructor.
-   * @return the constructor term
-   */
-  public Term getConstructorTerm()
-  {
-    long termPointer = getConstructorTerm(pointer);
-    return new Term(solver, termPointer);
-  }
-
-  private native long getConstructorTerm(long pointer);
-
-  /**
-   * Get the constructor operator of this datatype constructor whose return
-   * type is retSort. This method is intended to be used on constructors of
-   * parametric datatypes and can be seen as returning the constructor
-   * term that has been explicitly cast to the given sort.
-   *
-   * This method is required for constructors of parametric datatypes whose
-   * return type cannot be determined by type inference. For example, given:
-   *   (declare-datatype List (par (T) ((nil) (cons (head T) (tail (List T))))))
-   * The type of nil terms need to be provided by the user. In SMT version 2.6,
-   * this is done via the syntax for qualified identifiers:
-   *   (as nil (List Int))
-   * This method is equivalent of applying the above, where this
-   * DatatypeConstructor is the one corresponding to nil, and retSort is
-   * (List Int).
-   *
-   * Furthermore note that the returned constructor term t is an operator,
-   * while Solver::mkTerm(APPLY_CONSTRUCTOR, t) is used to construct the above
-   * (nullary) application of nil.
-   *
-   * @param retSort the desired return sort of the constructor
-   * @return the constructor term
-   */
-  public Term getSpecializedConstructorTerm(Sort retSort)
-  {
-    long termPointer = getSpecializedConstructorTerm(pointer, retSort.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long getSpecializedConstructorTerm(long pointer, long retSortPointer);
-
-  /**
-   * Get the tester operator of this datatype constructor.
-   * @return the tester operator
-   */
-  public Term getTesterTerm()
-  {
-    long termPointer = getTesterTerm(pointer);
-    return new Term(solver, termPointer);
-  }
-  private native long getTesterTerm(long pointer);
-
-  /**
-   * @return the number of selectors (so far) of this Datatype constructor.
-   */
-  public int getNumSelectors()
-  {
-    return getNumSelectors(pointer);
-  }
-  private native int getNumSelectors(long pointer);
-
-  /** @return the i^th DatatypeSelector. */
-  public DatatypeSelector getSelector(int index)
-  {
-    long selectorPointer = getSelector(pointer, index);
-    return new DatatypeSelector(solver, selectorPointer);
-  }
-  private native long getSelector(long pointer, int index);
-
-  /**
-   * Get the datatype selector with the given name.
-   * This is a linear search through the selectors, so in case of
-   * multiple, similarly-named selectors, the first is returned.
-   * @param name the name of the datatype selector
-   * @return the first datatype selector with the given name
-   */
-  public DatatypeSelector getSelector(String name)
-  {
-    long selectorPointer = getSelector(pointer, name);
-    return new DatatypeSelector(solver, selectorPointer);
-  }
-  private native long getSelector(long pointer, String name);
-
-  /**
-   * Get the term representation of the datatype selector with the given name.
-   * This is a linear search through the arguments, so in case of multiple,
-   * similarly-named arguments, the selector for the first is returned.
-   * @param name the name of the datatype selector
-   * @return a term representing the datatype selector with the given name
-   */
-  public Term getSelectorTerm(String name)
-  {
-    long termPointer = getSelectorTerm(pointer, name);
-    return new Term(solver, termPointer);
-  }
-  private native long getSelectorTerm(long pointer, String name);
-
-  /**
-   * @return true if this DatatypeConstructor is a null object
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * @return a string representation of this datatype constructor
-   */
-  protected native String toString(long pointer);
-
-  public class ConstIterator implements Iterator<DatatypeSelector>
-  {
-    private int currentIndex;
-    private int size;
-
-    public ConstIterator()
-    {
-      currentIndex = -1;
-      size = getNumSelectors();
-    }
-
-    @Override public boolean hasNext()
-    {
-      return currentIndex < size - 1;
-    }
-
-    @Override public DatatypeSelector next()
-    {
-      if (currentIndex >= size - 1)
-      {
-        throw new NoSuchElementException();
-      }
-      currentIndex++;
-
-      return getSelector(currentIndex);
-    }
-  }
-
-  @Override public Iterator<DatatypeSelector> iterator()
-  {
-    return new ConstIterator();
-  }
-}
diff --git a/src/api/java/cvc5/DatatypeConstructorDecl.java b/src/api/java/cvc5/DatatypeConstructorDecl.java
deleted file mode 100644 (file)
index 9769aa2..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class DatatypeConstructorDecl extends AbstractPointer
-{
-  // region construction and destruction
-  DatatypeConstructorDecl(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * Add datatype selector declaration.
-   * @param name the name of the datatype selector declaration to add
-   * @param sort the range sort of the datatype selector declaration to add
-   */
-  public void addSelector(String name, Sort sort)
-  {
-    addSelector(pointer, name, sort.getPointer());
-  }
-
-  private native void addSelector(long pointer, String name, long sortPointer);
-
-  /**
-   * Add datatype selector declaration whose range type is the datatype itself.
-   * @param name the name of the datatype selector declaration to add
-   */
-  public void addSelectorSelf(String name)
-  {
-    addSelectorSelf(pointer, name);
-  }
-
-  private native void addSelectorSelf(long pointer, String name);
-
-  /**
-   * @return true if this DatatypeConstructorDecl is a null declaration.
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * @return a string representation of this datatype constructor declaration
-   */
-  protected native String toString(long pointer);
-}
diff --git a/src/api/java/cvc5/DatatypeDecl.java b/src/api/java/cvc5/DatatypeDecl.java
deleted file mode 100644 (file)
index fa78c68..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class DatatypeDecl extends AbstractPointer
-{
-  // region construction and destruction
-  DatatypeDecl(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-  /**
-   * Add datatype constructor declaration.
-   * @param ctor the datatype constructor declaration to add
-   */
-  public void addConstructor(DatatypeConstructorDecl ctor)
-  {
-    addConstructor(pointer, ctor.getPointer());
-  }
-
-  private native void addConstructor(long pointer, long declPointer);
-
-  /** Get the number of constructors (so far) for this Datatype declaration. */
-  int getNumConstructors()
-  {
-    return getNumConstructors(pointer);
-  }
-
-  private native int getNumConstructors(long pointer);
-
-  /** Is this Datatype declaration parametric? */
-  public boolean isParametric()
-  {
-    return isParametric(pointer);
-  }
-
-  private native boolean isParametric(long pointer);
-
-  /**
-   * @return true if this DatatypeDecl is a null object
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * @return a string representation of this datatype declaration
-   */
-  protected native String toString(long pointer);
-
-  /** @return the name of this datatype declaration. */
-  public String getName()
-  {
-    return getName(pointer);
-  }
-
-  private native String getName(long pointer);
-}
diff --git a/src/api/java/cvc5/DatatypeSelector.java b/src/api/java/cvc5/DatatypeSelector.java
deleted file mode 100644 (file)
index 014c35d..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class DatatypeSelector extends AbstractPointer
-{
-  // region construction and destruction
-  DatatypeSelector(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /** @return the name of this Datatype selector. */
-  String getName()
-  {
-    return getName(pointer);
-  }
-
-  private native String getName(long pointer);
-
-  /**
-   * Get the selector operator of this datatype selector.
-   * @return the selector term
-   */
-  public Term getSelectorTerm()
-  {
-    long termPointer = getSelectorTerm(pointer);
-    return new Term(solver, termPointer);
-  }
-
-  private native long getSelectorTerm(long pointer);
-
-  /**
-   * Get the upater operator of this datatype selector.
-   * @return the updater term
-   */
-  public Term getUpdaterTerm()
-  {
-    long termPointer = getUpdaterTerm(pointer);
-    return new Term(solver, termPointer);
-  }
-
-  private native long getUpdaterTerm(long pointer);
-
-  /** @return the range sort of this selector. */
-  Sort getRangeSort()
-  {
-    long sortPointer = getRangeSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getRangeSort(long pointer);
-
-  /**
-   * @return true if this DatatypeSelector is a null object
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * @return a string representation of this datatype selector
-   */
-  protected native String toString(long pointer);
-}
diff --git a/src/api/java/cvc5/Grammar.java b/src/api/java/cvc5/Grammar.java
deleted file mode 100644 (file)
index b9240a6..0000000
+++ /dev/null
@@ -1,99 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class Grammar extends AbstractPointer
-{
-  // region construction and destruction
-  Grammar(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  public Grammar(Grammar grammar)
-  {
-    super(grammar.solver, copyGrammar(grammar.pointer));
-  }
-
-  private static native long copyGrammar(long pointer);
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * Add \p rule to the set of rules corresponding to \p ntSymbol.
-   * @param ntSymbol the non-terminal to which the rule is added
-   * @param rule the rule to add
-   */
-  public void addRule(Term ntSymbol, Term rule)
-  {
-    addRule(pointer, ntSymbol.getPointer(), rule.getPointer());
-  }
-
-  private native void addRule(long pointer, long ntSymbolPointer, long rulePointer);
-
-  /**
-   * Add \p rules to the set of rules corresponding to \p ntSymbol.
-   * @param ntSymbol the non-terminal to which the rules are added
-   * @param rules the rules to add
-   */
-  public void addRules(Term ntSymbol, Term[] rules)
-  {
-    long[] pointers = Utils.getPointers(rules);
-    addRules(pointer, ntSymbol.getPointer(), pointers);
-  }
-
-  public native void addRules(long pointer, long ntSymbolPointer, long[] rulePointers);
-
-  /**
-   * Allow \p ntSymbol to be an arbitrary constant.
-   * @param ntSymbol the non-terminal allowed to be any constant
-   */
-  public void addAnyConstant(Term ntSymbol)
-  {
-    addAnyConstant(pointer, ntSymbol.getPointer());
-  }
-
-  private native void addAnyConstant(long pointer, long ntSymbolPointer);
-
-  /**
-   * Allow \p ntSymbol to be any input variable to corresponding
-   * synth-fun/synth-inv with the same sort as \p ntSymbol.
-   * @param ntSymbol the non-terminal allowed to be any input constant
-   */
-  public void addAnyVariable(Term ntSymbol)
-  {
-    addAnyVariable(pointer, ntSymbol.getPointer());
-  }
-
-  private native void addAnyVariable(long pointer, long ntSymbolPointer);
-
-  /**
-   * @return a string representation of this grammar.
-   */
-  protected native String toString(long pointer);
-}
diff --git a/src/api/java/cvc5/IPointer.java b/src/api/java/cvc5/IPointer.java
deleted file mode 100644 (file)
index 17d6d59..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-interface IPointer {
-  long getPointer();
-}
diff --git a/src/api/java/cvc5/Op.java b/src/api/java/cvc5/Op.java
deleted file mode 100644 (file)
index bf908af..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class Op extends AbstractPointer
-{
-  // region construction and destruction
-  Op(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * Syntactic equality operator.
-   * Return true if both operators are syntactically identical.
-   * Both operators must belong to the same solver object.
-   * @param t the operator to compare to for equality
-   * @return true if the operators are equal
-   */
-  @Override public boolean equals(Object t)
-  {
-    if (this == t)
-      return true;
-    if (t == null || getClass() != t.getClass())
-      return false;
-    return equals(pointer, ((Op) t).getPointer());
-  }
-
-  private native boolean equals(long pointer1, long pointer2);
-
-  /**
-   * @return the kind of this operator
-   */
-  public Kind getKind()
-  {
-    try
-    {
-      int value = getKind(pointer);
-      return Kind.fromInt(value);
-    }
-    catch (CVC5ApiException e)
-    {
-      e.printStackTrace();
-      throw new RuntimeException(e.getMessage());
-    }
-  }
-
-  private native int getKind(long pointer);
-
-  /**
-   * @return true if this operator is a null term
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * @return true iff this operator is indexed
-   */
-  public boolean isIndexed()
-  {
-    return isIndexed(pointer);
-  }
-
-  private native boolean isIndexed(long pointer);
-
-  /**
-   * @return the number of indices of this op
-   */
-  public int getNumIndices()
-  {
-    return getNumIndices(pointer);
-  }
-
-  private native int getNumIndices(long pointer);
-
-  /**
-   * Get the indices used to create this Op.
-   * Check the Op Kind with getKind() to determine which argument to use.
-   *
-   * @return the indices used to create this Op
-   */
-  public int[] getIntegerIndices()
-  {
-    return getIntegerIndices(pointer);
-  }
-
-  private native int[] getIntegerIndices(long pointer);
-
-  /**
-   * Get the indices used to create this Op.
-   * Check the Op Kind with getKind() to determine which argument to use.
-   *
-   * @return the indices used to create this Op
-   */
-  public String[] getStringIndices()
-  {
-    return getStringIndices(pointer);
-  }
-
-  private native String[] getStringIndices(long pointer);
-
-  /**
-   * @return a string representation of this operator
-   */
-  protected native String toString(long pointer);
-}
diff --git a/src/api/java/cvc5/OptionInfo.java b/src/api/java/cvc5/OptionInfo.java
deleted file mode 100644 (file)
index 7690a1b..0000000
+++ /dev/null
@@ -1,209 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Gereon Kremer, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.math.BigInteger;
-
-/**
- * Holds some description about a particular option, including its name, its
- * aliases, whether the option was explicitly set by the user, and information
- * concerning its value. The `valueInfo` member holds any of the following
- * alternatives:
- * - VoidInfo if the option holds no value (or the value has no native type)
- * - ValueInfo if the option is of type boolean or String, holds the
- *   current value and the default value.
- * - NumberInfo if the option is of type BigInteger or double, holds
- *   the current and default value, as well as the minimum and maximum.
- * - ModeInfo if the option is a mode option, holds the current and default
- *   values, as well as a list of valid modes.
- * Additionally, this class provides convenience functions to obtain the
- * current value of an option in a type-safe manner using boolValue(),
- * stringValue(), intValue(), and doubleValue(). They assert that
- * the option has the respective type and return the current value.
- */
-public class OptionInfo extends AbstractPointer
-{
-  // region construction and destruction
-  OptionInfo(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-    this.name = getName(pointer);
-    this.aliases = getAliases(pointer);
-    this.setByUser = getSetByUser(pointer);
-    this.baseInfo = getBaseInfo(pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  /**
-   * @return a string representation of this optionInfo.
-   */
-  protected native String toString(long pointer);
-
-  // endregion
-
-  /** Abstract class for OptionInfo values */
-  abstract class BaseInfo
-  {
-  }
-
-  /** Has the current and the default value */
-  public abstract class ValueInfo<T> extends BaseInfo
-  {
-    private final T defaultValue;
-    private final T currentValue;
-    public ValueInfo(T defaultValue, T currentValue)
-    {
-      this.defaultValue = defaultValue;
-      this.currentValue = currentValue;
-    }
-    public T getDefaultValue()
-    {
-      return defaultValue;
-    }
-    public T getCurrentValue()
-    {
-      return currentValue;
-    }
-  }
-
-  public class ModeInfo extends ValueInfo<String>
-  {
-    private final String[] modes;
-
-    public ModeInfo(String defaultValue, String currentValue, String[] modes)
-    {
-      super(defaultValue, currentValue);
-      this.modes = modes;
-    }
-    public String[] getModes()
-    {
-      return modes;
-    }
-  }
-
-  /** Has no value information */
-  public class VoidInfo extends BaseInfo
-  {
-  }
-
-  /** Default value, current value, minimum and maximum of a numeric value */
-  public class NumberInfo<T> extends ValueInfo<T>
-  {
-    private final T minimum;
-    private final T maximum;
-    public NumberInfo(T defaultValue, T currentValue, T minimum, T maximum)
-    {
-      super(defaultValue, currentValue);
-      this.minimum = minimum;
-      this.maximum = maximum;
-    }
-    public T getMinimum()
-    {
-      return minimum;
-    }
-    public T getMaximum()
-    {
-      return maximum;
-    }
-  }
-
-  private native String getName(long pointer);
-
-  private native String[] getAliases(long pointer);
-
-  private native boolean getSetByUser(long pointer);
-
-  private native BaseInfo getBaseInfo(long pointer);
-
-  /** The option name */
-  private final String name;
-  public String getName()
-  {
-    return name;
-  }
-  /** The option name aliases */
-  private final String[] aliases;
-  public String[] getAliases()
-  {
-    return aliases;
-  }
-  /** Whether the option was explicitly set by the user */
-  private final boolean setByUser;
-  public boolean getSetByUser()
-  {
-    return setByUser;
-  }
-
-  /** The option variant information */
-  private final BaseInfo baseInfo;
-  public BaseInfo getBaseInfo()
-  {
-    return baseInfo;
-  }
-
-  /**
-   * Obtain the current value as a boolean. Asserts that valueInfo holds a boolean.
-   */
-  public boolean booleanValue()
-  {
-    return booleanValue(pointer);
-  }
-
-  private native boolean booleanValue(long pointer);
-
-  /**
-   * Obtain the current value as a string. Asserts that valueInfo holds a
-   * string.
-   */
-  public String stringValue()
-  {
-    return stringValue(pointer);
-  }
-
-  private native String stringValue(long pointer);
-
-  /**
-   * Obtain the current value as as int. Asserts that valueInfo holds an int.
-   */
-  public BigInteger intValue()
-  {
-    return intValue(pointer);
-  }
-
-  private native BigInteger intValue(long pointer);
-
-  /**
-   * Obtain the current value as a double. Asserts that valueInfo holds a
-   * double.
-   */
-  public double doubleValue()
-  {
-    return doubleValue(pointer);
-  }
-
-  private native double doubleValue(long pointer);
-};
diff --git a/src/api/java/cvc5/Pair.java b/src/api/java/cvc5/Pair.java
deleted file mode 100644 (file)
index 84c9d8e..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class Pair<K, V>
-{
-  public K first;
-  public V second;
-  public Pair(K first, V second)
-  {
-    this.first = first;
-    this.second = second;
-  }
-
-  @Override public boolean equals(Object pair)
-  {
-    if (this == pair)
-      return true;
-    if (pair == null || getClass() != pair.getClass())
-      return false;
-
-    Pair<K, V> p = (Pair<K, V>) pair;
-
-    return first.equals(p.first) && second.equals(p.second);
-  }
-}
diff --git a/src/api/java/cvc5/Result.java b/src/api/java/cvc5/Result.java
deleted file mode 100644 (file)
index 3573094..0000000
+++ /dev/null
@@ -1,208 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.util.HashMap;
-import java.util.Map;
-
-public class Result extends AbstractPointer
-{
-  // region construction and destruction
-  Result(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  public enum UnknownExplanation {
-    REQUIRES_FULL_CHECK(0),
-    INCOMPLETE(1),
-    TIMEOUT(2),
-    RESOURCEOUT(3),
-    MEMOUT(4),
-    INTERRUPTED(5),
-    NO_STATUS(6),
-    UNSUPPORTED(7),
-    OTHER(8),
-    UNKNOWN_REASON(9);
-
-    /* the int value of the UnknownExplanation */
-    private int value;
-    private static Map<Integer, UnknownExplanation> explanationMap = new HashMap<>();
-    private UnknownExplanation(int value)
-    {
-      this.value = value;
-    }
-
-    static
-    {
-      for (UnknownExplanation explanation : UnknownExplanation.values())
-      {
-        explanationMap.put(explanation.getValue(), explanation);
-      }
-    }
-
-    public static UnknownExplanation fromInt(int value) throws CVC5ApiException
-    {
-      if (value < REQUIRES_FULL_CHECK.value || value > UNKNOWN_REASON.value)
-      {
-        throw new CVC5ApiException("UnknownExplanation value " + value
-            + " is outside the valid range [" + REQUIRES_FULL_CHECK.value + ","
-            + UNKNOWN_REASON.value + "]");
-      }
-      return explanationMap.get(value);
-    }
-
-    public int getValue()
-    {
-      return value;
-    }
-  }
-
-  /**
-   * Return true if Result is empty, i.e., a nullary Result, and not an actual
-   * result returned from a checkSat() (and friends) query.
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * Return true if query was a satisfiable checkSat() or checkSatAssuming()
-   * query.
-   */
-  public boolean isSat()
-  {
-    return isSat(pointer);
-  }
-
-  private native boolean isSat(long pointer);
-
-  /**
-   * Return true if query was an unsatisfiable checkSat() or
-   * checkSatAssuming() query.
-   */
-  public boolean isUnsat()
-  {
-    return isUnsat(pointer);
-  }
-
-  private native boolean isUnsat(long pointer);
-
-  /**
-   * Return true if query was a checkSat() or checkSatAssuming() query and
-   * cvc5 was not able to determine (un)satisfiability.
-   */
-  public boolean isSatUnknown()
-  {
-    return isSatUnknown(pointer);
-  }
-
-  private native boolean isSatUnknown(long pointer);
-
-  /**
-   * Return true if corresponding query was an entailed checkEntailed() query.
-   */
-  public boolean isEntailed()
-  {
-    return isEntailed(pointer);
-  }
-
-  private native boolean isEntailed(long pointer);
-
-  /**
-   * Return true if corresponding query was a checkEntailed() query that is
-   * not entailed.
-   */
-  public boolean isNotEntailed()
-  {
-    return isNotEntailed(pointer);
-  }
-
-  private native boolean isNotEntailed(long pointer);
-
-  /**
-   * Return true if query was a checkEntailed() query and cvc5 was not able to
-   * determine if it is entailed.
-   */
-  public boolean isEntailmentUnknown()
-  {
-    return isEntailmentUnknown(pointer);
-  }
-
-  private native boolean isEntailmentUnknown(long pointer);
-
-  /**
-   * Operator overloading for equality of two results.
-   * @param r the result to compare to for equality
-   * @return true if the results are equal
-   */
-  @Override public boolean equals(Object r)
-  {
-    if (this == r)
-      return true;
-    if (r == null || getClass() != r.getClass())
-      return false;
-    Result result = (Result) r;
-    if (this.pointer == result.pointer)
-    {
-      return true;
-    }
-    return equals(pointer, result.getPointer());
-  }
-
-  private native boolean equals(long pointer1, long pointer2);
-
-  /**
-   * @return an explanation for an unknown query result.
-   */
-  public UnknownExplanation getUnknownExplanation()
-  {
-    try
-    {
-      int explanation = getUnknownExplanation(pointer);
-      return UnknownExplanation.fromInt(explanation);
-    }
-    catch (CVC5ApiException e)
-    {
-      e.printStackTrace();
-      throw new RuntimeException(e.getMessage());
-    }
-  }
-
-  private native int getUnknownExplanation(long pointer);
-
-  /**
-   * @return a string representation of this result.
-   */
-  protected native String toString(long pointer);
-}
diff --git a/src/api/java/cvc5/RoundingMode.java b/src/api/java/cvc5/RoundingMode.java
deleted file mode 100644 (file)
index 4229bb7..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public enum RoundingMode {
-  /**
-   * Round to the nearest even number.
-   * If the two nearest floating-point numbers bracketing an unrepresentable
-   * infinitely precise result are equally near, the one with an even least
-   * significant digit will be delivered.
-   */
-  ROUND_NEAREST_TIES_TO_EVEN(0),
-  /**
-   * Round towards positive infinity (+oo).
-   * The result shall be the format’s floating-point number (possibly +oo)
-   * closest to and no less than the infinitely precise result.
-   */
-  ROUND_TOWARD_POSITIVE(1),
-  /**
-   * Round towards negative infinity (-oo).
-   * The result shall be the format’s floating-point number (possibly -oo)
-   * closest to and no less than the infinitely precise result.
-   */
-  ROUND_TOWARD_NEGATIVE(2),
-  /**
-   * Round towards zero.
-   * The result shall be the format’s floating-point number closest to and no
-   * greater in magnitude than the infinitely precise result.
-   */
-  ROUND_TOWARD_ZERO(3),
-  /**
-   * Round to the nearest number away from zero.
-   * If the two nearest floating-point numbers bracketing an unrepresentable
-   * infinitely precise result are equally near, the one with larger magnitude
-   * will be selected.
-   */
-  ROUND_NEAREST_TIES_TO_AWAY(4);
-
-  private int value;
-
-  private RoundingMode(int value)
-  {
-    this.value = value;
-  }
-
-  public int getValue()
-  {
-    return value;
-  }
-}
diff --git a/src/api/java/cvc5/Solver.java b/src/api/java/cvc5/Solver.java
deleted file mode 100644 (file)
index cc57975..0000000
+++ /dev/null
@@ -1,2654 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.io.IOException;
-import java.util.*;
-
-public class Solver implements IPointer
-{
-  private final long pointer;
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  private native long newSolver();
-
-  public void deletePointer()
-  {
-    deletePointer(pointer);
-  }
-
-  private static native void deletePointer(long pointer);
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  static
-  {
-    Utils.loadLibraries();
-  }
-
-  /* .................................................................... */
-  /* Constructors                                                         */
-  /* .................................................................... */
-
-  public Solver()
-  {
-    this.pointer = newSolver();
-  }
-
-  /* .................................................................... */
-  /* Sorts Handling                                                       */
-  /* .................................................................... */
-
-  /**
-   * @return sort null
-   */
-
-  public Sort getNullSort()
-  {
-    long sortPointer = getNullSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long getNullSort(long pointer);
-
-  /**
-   * @return sort Boolean
-   */
-  public Sort getBooleanSort()
-  {
-    long sortPointer = getBooleanSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long getBooleanSort(long pointer);
-
-  /**
-   * @return sort Integer (in cvc5, Integer is a subtype of Real)
-   */
-  public Sort getIntegerSort()
-  {
-    long sortPointer = getIntegerSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  public native long getIntegerSort(long pointer);
-  /**
-   * @return sort Real
-   */
-  public Sort getRealSort()
-  {
-    long sortPointer = getRealSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long getRealSort(long pointer);
-  /**
-   * @return sort RegExp
-   */
-  public Sort getRegExpSort()
-  {
-    long sortPointer = getRegExpSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long getRegExpSort(long pointer);
-  /**
-   * @return sort RoundingMode
-   */
-  public Sort getRoundingModeSort() throws CVC5ApiException
-  {
-    long sortPointer = getRoundingModeSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long getRoundingModeSort(long pointer) throws CVC5ApiException;
-  /**
-   * @return sort String
-   */
-  public Sort getStringSort()
-  {
-    long sortPointer = getStringSort(pointer);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long getStringSort(long solverPointer);
-  /**
-   * Create an array sort.
-   * @param indexSort the array index sort
-   * @param elemSort the array element sort
-   * @return the array sort
-   */
-  public Sort mkArraySort(Sort indexSort, Sort elemSort)
-  {
-    long sortPointer = mkArraySort(pointer, indexSort.getPointer(), elemSort.getPointer());
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkArraySort(long pointer, long indexSortPointer, long elementSortPointer);
-
-  /**
-   * Create a bit-vector sort.
-   * @param size the bit-width of the bit-vector sort
-   * @return the bit-vector sort
-   */
-  public Sort mkBitVectorSort(int size) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(size, "size");
-    long sortPointer = mkBitVectorSort(pointer, size);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkBitVectorSort(long pointer, int size);
-
-  /**
-   * Create a floating-point sort.
-   * @param exp the bit-width of the exponent of the floating-point sort.
-   * @param sig the bit-width of the significand of the floating-point sort.
-   */
-  public Sort mkFloatingPointSort(int exp, int sig) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long sortPointer = mkFloatingPointSort(pointer, exp, sig);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkFloatingPointSort(long solverPointer, int exp, int sig);
-
-  /**
-   * Create a datatype sort.
-   * @param dtypedecl the datatype declaration from which the sort is
-   *     created
-   * @return the datatype sort
-   */
-  public Sort mkDatatypeSort(DatatypeDecl dtypedecl) throws CVC5ApiException
-  {
-    long pointer = mkDatatypeSort(this.pointer, dtypedecl.getPointer());
-    return new Sort(this, pointer);
-  }
-
-  private native long mkDatatypeSort(long pointer, long datatypeDeclPointer)
-      throws CVC5ApiException;
-
-  /**
-   * Create a vector of datatype sorts. The names of the datatype
-   * declarations must be distinct.
-   *
-   * @param dtypedecls the datatype declarations from which the sort is
-   *     created
-   * @return the datatype sorts
-   */
-  public Sort[] mkDatatypeSorts(List<DatatypeDecl> dtypedecls) throws CVC5ApiException
-  {
-    return mkDatatypeSorts(dtypedecls.toArray(new DatatypeDecl[0]));
-  }
-
-  /**
-   * Create a vector of datatype sorts. The names of the datatype
-   * declarations must be distinct.
-   *
-   * @param dtypedecls the datatype declarations from which the sort is
-   *     created
-   * @return the datatype sorts
-   */
-  public Sort[] mkDatatypeSorts(DatatypeDecl[] dtypedecls) throws CVC5ApiException
-  {
-    long[] declPointers = Utils.getPointers(dtypedecls);
-    long[] sortPointers = mkDatatypeSorts(pointer, declPointers);
-    Sort[] sorts = Utils.getSorts(this, sortPointers);
-    return sorts;
-  }
-
-  private native long[] mkDatatypeSorts(long pointer, long[] declPointers) throws CVC5ApiException;
-
-  /**
-   * Create a vector of datatype sorts using unresolved sorts. The names of
-   * the datatype declarations in dtypedecls must be distinct.
-   *
-   * This method is called when the DatatypeDecl objects dtypedecls have
-   * been built using "unresolved" sorts.
-   *
-   * We associate each sort in unresolvedSorts with exacly one datatype from
-   * dtypedecls. In particular, it must have the same name as exactly one
-   * datatype declaration in dtypedecls.
-   *
-   * When constructing datatypes, unresolved sorts are replaced by the
-   * datatype sort constructed for the datatype declaration it is associated
-   * with.
-   *
-   * @param dtypedecls the datatype declarations from which the sort is
-   *     created
-   * @param unresolvedSorts the set of unresolved sorts
-   * @return the datatype sorts
-   */
-  public List<Sort> mkDatatypeSorts(List<DatatypeDecl> dtypedecls, Set<Sort> unresolvedSorts)
-      throws CVC5ApiException
-  {
-    Sort[] array = mkDatatypeSorts(
-        dtypedecls.toArray(new DatatypeDecl[0]), unresolvedSorts.toArray(new Sort[0]));
-    return Arrays.asList(array);
-  }
-
-  /**
-   * Create a vector of datatype sorts using unresolved sorts. The names of
-   * the datatype declarations in dtypedecls must be distinct.
-   *
-   * This method is called when the DatatypeDecl objects dtypedecls have
-   * been built using "unresolved" sorts.
-   *
-   * We associate each sort in unresolvedSorts with exacly one datatype from
-   * dtypedecls. In particular, it must have the same name as exactly one
-   * datatype declaration in dtypedecls.
-   *
-   * When constructing datatypes, unresolved sorts are replaced by the
-   * datatype sort constructed for the datatype declaration it is associated
-   * with.
-   *
-   * @param dtypedecls the datatype declarations from which the sort is
-   *     created
-   * @param unresolvedSorts the list of unresolved sorts
-   * @return the datatype sorts
-   */
-  public Sort[] mkDatatypeSorts(DatatypeDecl[] dtypedecls, Sort[] unresolvedSorts)
-      throws CVC5ApiException
-  {
-    long[] declPointers = Utils.getPointers(dtypedecls);
-    long[] unresolvedPointers = Utils.getPointers(unresolvedSorts);
-    long[] sortPointers = mkDatatypeSorts(pointer, declPointers, unresolvedPointers);
-    Sort[] sorts = Utils.getSorts(this, sortPointers);
-    return sorts;
-  }
-
-  private native long[] mkDatatypeSorts(
-      long pointer, long[] declPointers, long[] unresolvedPointers) throws CVC5ApiException;
-
-  /**
-   * Create function sort.
-   * @param domain the sort of the fuction argument
-   * @param codomain the sort of the function return value
-   * @return the function sort
-   */
-  public Sort mkFunctionSort(Sort domain, Sort codomain)
-  {
-    long sortPointer = mkFunctionSort(pointer, domain.getPointer(), codomain.getPointer());
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkFunctionSort(long pointer, long domainPointer, long codomainPointer);
-
-  /**
-   * Create function sort.
-   * @param sorts the sort of the function arguments
-   * @param codomain the sort of the function return value
-   * @return the function sort
-   */
-  public Sort mkFunctionSort(Sort[] sorts, Sort codomain)
-  {
-    long sortPointer = mkFunctionSort(pointer, Utils.getPointers(sorts), codomain.getPointer());
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkFunctionSort(long pointer, long[] sortPointers, long codomainPointer);
-
-  /**
-   * Create a sort parameter.
-   * @param symbol the name of the sort
-   * @return the sort parameter
-   */
-  public Sort mkParamSort(String symbol)
-  {
-    long sortPointer = mkParamSort(pointer, symbol);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkParamSort(long pointer, String symbol);
-
-  /**
-   * Create a predicate sort.
-   * @param sorts the list of sorts of the predicate
-   * @return the predicate sort
-   */
-  public Sort mkPredicateSort(Sort[] sorts)
-  {
-    long sortPointer = mkPredicateSort(pointer, Utils.getPointers(sorts));
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkPredicateSort(long pointer, long[] sortPointers);
-
-  /**
-   * Create a record sort
-   * @param fields the list of fields of the record
-   * @return the record sort
-   */
-  public Sort mkRecordSort(Pair<String, Sort>[] fields)
-  {
-    long sortPointer = mkRecordSort(pointer, Utils.getPairs(fields));
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkRecordSort(long pointer, Pair<String, Long>[] fields);
-
-  /**
-   * Create a set sort.
-   * @param elemSort the sort of the set elements
-   * @return the set sort
-   */
-  public Sort mkSetSort(Sort elemSort)
-  {
-    long sortPointer = mkSetSort(pointer, elemSort.getPointer());
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkSetSort(long pointer, long elemSortPointer);
-  /**
-   * Create a bag sort.
-   * @param elemSort the sort of the bag elements
-   * @return the bag sort
-   */
-  public Sort mkBagSort(Sort elemSort)
-  {
-    long sortPointer = mkBagSort(pointer, elemSort.getPointer());
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkBagSort(long pointer, long elemSortPointer);
-
-  /**
-   * Create a sequence sort.
-   * @param elemSort the sort of the sequence elements
-   * @return the sequence sort
-   */
-  public Sort mkSequenceSort(Sort elemSort)
-  {
-    long sortPointer = mkSequenceSort(pointer, elemSort.getPointer());
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkSequenceSort(long pointer, long elemSortPointer);
-
-  /**
-   * Create an uninterpreted sort.
-   * @param symbol the name of the sort
-   * @return the uninterpreted sort
-   */
-  public Sort mkUninterpretedSort(String symbol)
-  {
-    long sortPointer = mkUninterpretedSort(pointer, symbol);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkUninterpretedSort(long pointer, String symbol);
-
-  /**
-   * Create a sort constructor sort.
-   * @param symbol the symbol of the sort
-   * @param arity the arity of the sort
-   * @return the sort constructor sort
-   */
-  public Sort mkSortConstructorSort(String symbol, int arity) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(arity, "arity");
-    long sortPointer = mkSortConstructorSort(pointer, symbol, arity);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkSortConstructorSort(long pointer, String symbol, int arity);
-
-  /**
-   * Create a tuple sort.
-   * @param sorts of the elements of the tuple
-   * @return the tuple sort
-   */
-  public Sort mkTupleSort(Sort[] sorts)
-  {
-    long[] sortPointers = Utils.getPointers(sorts);
-    long sortPointer = mkTupleSort(pointer, sortPointers);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long mkTupleSort(long pointer, long[] sortPointers);
-
-  /* .................................................................... */
-  /* Create Terms                                                         */
-  /* .................................................................... */
-
-  /**
-   * Create 0-ary term of given kind.
-   * @param kind the kind of the term
-   * @return the Term
-   */
-  public Term mkTerm(Kind kind)
-  {
-    long termPointer = mkTerm(pointer, kind.getValue());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, int kindValue);
-
-  /**
-   * Create a unary term of given kind.
-   * @param kind the kind of the term
-   * @param child the child of the term
-   * @return the Term
-   */
-  public Term mkTerm(Kind kind, Term child)
-  {
-    long termPointer = mkTerm(pointer, kind.getValue(), child.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, int kindValue, long childPointer);
-
-  /**
-   * Create binary term of given kind.
-   * @param kind the kind of the term
-   * @param child1 the first child of the term
-   * @param child2 the second child of the term
-   * @return the Term
-   */
-  public Term mkTerm(Kind kind, Term child1, Term child2)
-  {
-    long termPointer = mkTerm(pointer, kind.getValue(), child1.getPointer(), child2.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, int kindValue, long child1Pointer, long child2Pointer);
-
-  /**
-   * Create ternary term of given kind.
-   * @param kind the kind of the term
-   * @param child1 the first child of the term
-   * @param child2 the second child of the term
-   * @param child3 the third child of the term
-   * @return the Term
-   */
-  public Term mkTerm(Kind kind, Term child1, Term child2, Term child3)
-  {
-    long termPointer = mkTerm(
-        pointer, kind.getValue(), child1.getPointer(), child2.getPointer(), child3.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(
-      long pointer, int kindValue, long child1Pointer, long child2Pointer, long child3Pointer);
-  /**
-   * Create n-ary term of given kind.
-   * @param kind the kind of the term
-   * @param children the children of the term
-   * @return the Term
-   */
-  public Term mkTerm(Kind kind, Term[] children)
-  {
-    long[] childPointers = Utils.getPointers(children);
-    long termPointer = mkTerm(pointer, kind.getValue(), childPointers);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, int kindValue, long[] childrenPointers);
-
-  /**
-   * Create nullary term of given kind from a given operator.
-   * Create operators with mkOp().
-   * @param op the operator
-   * @return the Term
-   */
-  public Term mkTerm(Op op)
-  {
-    long termPointer = mkTerm(pointer, op.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, long opPointer);
-  /**
-   * Create unary term of given kind from a given operator.
-   * Create operators with mkOp().
-   * @param op the operator
-   * @param child the child of the term
-   * @return the Term
-   */
-  public Term mkTerm(Op op, Term child)
-  {
-    long termPointer = mkTerm(pointer, op.getPointer(), child.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, long opPointer, long childPointer);
-
-  /**
-   * Create binary term of given kind from a given operator.
-   * Create operators with mkOp().
-   * @param op the operator
-   * @param child1 the first child of the term
-   * @param child2 the second child of the term
-   * @return the Term
-   */
-  public Term mkTerm(Op op, Term child1, Term child2)
-  {
-    long termPointer = mkTerm(pointer, op.getPointer(), child1.getPointer(), child2.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, long opPointer, long child1Pointer, long child2Pointer);
-  /**
-   * Create ternary term of given kind from a given operator.
-   * Create operators with mkOp().
-   * @param op the operator
-   * @param child1 the first child of the term
-   * @param child2 the second child of the term
-   * @param child3 the third child of the term
-   * @return the Term
-   */
-  public Term mkTerm(Op op, Term child1, Term child2, Term child3)
-  {
-    long termPointer =
-        mkTerm(op.getPointer(), child1.getPointer(), child2.getPointer(), child3.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(
-      long pointer, long opPointer, long child1Pointer, long child2Pointer, long child3Pointer);
-
-  /**
-   * Create n-ary term of given kind from a given operator.
-   * Create operators with mkOp().
-   * @param op the operator
-   * @param children the children of the term
-   * @return the Term
-   */
-  public Term mkTerm(Op op, List<Term> children)
-  {
-    return mkTerm(op, children.toArray(new Term[0]));
-  }
-
-  /**
-   * Create n-ary term of given kind from a given operator.
-   * Create operators with mkOp().
-   * @param op the operator
-   * @param children the children of the term
-   * @return the Term
-   */
-  public Term mkTerm(Op op, Term[] children)
-  {
-    long[] childPointers = Utils.getPointers(children);
-    long termPointer = mkTerm(pointer, op.getPointer(), childPointers);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTerm(long pointer, long opPointer, long[] childrenPointers);
-
-  /**
-   * Create a tuple term. Terms are automatically converted if sorts are
-   * compatible.
-   * @param sorts The sorts of the elements in the tuple
-   * @param terms The elements in the tuple
-   * @return the tuple Term
-   */
-  public Term mkTuple(Sort[] sorts, Term[] terms)
-  {
-    long[] sortPointers = Utils.getPointers(sorts);
-    long[] termPointers = Utils.getPointers(terms);
-    long termPointer = mkTuple(pointer, sortPointers, termPointers);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTuple(long pointer, long[] sortPointers, long[] termPointers);
-
-  /* .................................................................... */
-  /* Create Operators                                                     */
-  /* .................................................................... */
-
-  /**
-   * Create an operator for a builtin Kind
-   * The Kind may not be the Kind for an indexed operator
-   *   (e.g. BITVECTOR_EXTRACT)
-   * Note: in this case, the Op simply wraps the Kind.
-   * The Kind can be used in mkTerm directly without
-   *   creating an op first.
-   * @param kind the kind to wrap
-   */
-  public Op mkOp(Kind kind)
-  {
-    long opPointer = mkOp(pointer, kind.getValue());
-    return new Op(this, opPointer);
-  }
-
-  private native long mkOp(long pointer, int kindValue);
-  /**
-   * Create operator of kind:
-   *   - RECORD_UPDATE
-   *   - DIVISIBLE (to support arbitrary precision integers)
-   * See enum Kind for a description of the parameters.
-   * @param kind the kind of the operator
-   * @param arg the string argument to this operator
-   */
-  public Op mkOp(Kind kind, String arg)
-  {
-    long opPointer = mkOp(pointer, kind.getValue(), arg);
-    return new Op(this, opPointer);
-  }
-
-  private native long mkOp(long pointer, int kindValue, String arg);
-
-  /**
-   * Create operator of kind:
-   *   - DIVISIBLE
-   *   - BITVECTOR_REPEAT
-   *   - BITVECTOR_ZERO_EXTEND
-   *   - BITVECTOR_SIGN_EXTEND
-   *   - BITVECTOR_ROTATE_LEFT
-   *   - BITVECTOR_ROTATE_RIGHT
-   *   - INT_TO_BITVECTOR
-   *   - FLOATINGPOINT_TO_UBV
-   *   - FLOATINGPOINT_TO_UBV_TOTAL
-   *   - FLOATINGPOINT_TO_SBV
-   *   - FLOATINGPOINT_TO_SBV_TOTAL
-   *   - TUPLE_UPDATE
-   * See enum Kind for a description of the parameters.
-   * @param kind the kind of the operator
-   * @param arg the unsigned int argument to this operator
-   */
-  public Op mkOp(Kind kind, int arg) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(arg, "arg");
-    long opPointer = mkOp(pointer, kind.getValue(), arg);
-    return new Op(this, opPointer);
-  }
-
-  private native long mkOp(long pointer, int kindValue, int arg);
-
-  /**
-   * Create operator of Kind:
-   *   - BITVECTOR_EXTRACT
-   *   - FLOATINGPOINT_TO_FP_IEEE_BITVECTOR
-   *   - FLOATINGPOINT_TO_FP_FLOATINGPOINT
-   *   - FLOATINGPOINT_TO_FP_REAL
-   *   - FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR
-   *   - FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR
-   *   - FLOATINGPOINT_TO_FP_GENERIC
-   * See enum Kind for a description of the parameters.
-   * @param kind the kind of the operator
-   * @param arg1 the first unsigned int argument to this operator
-   * @param arg2 the second unsigned int argument to this operator
-   */
-  public Op mkOp(Kind kind, int arg1, int arg2) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(arg1, "arg1");
-    Utils.validateUnsigned(arg2, "arg2");
-    long opPointer = mkOp(pointer, kind.getValue(), arg1, arg2);
-    return new Op(this, opPointer);
-  }
-
-  private native long mkOp(long pointer, int kindValue, int arg1, int arg2);
-
-  /**
-   * Create operator of Kind:
-   *   - TUPLE_PROJECT
-   * See enum Kind for a description of the parameters.
-   * @param kind the kind of the operator
-   * @param args the arguments (indices) of the operator
-   */
-  public Op mkOp(Kind kind, int[] args) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(args, "args");
-    long opPointer = mkOp(pointer, kind.getValue(), args);
-    return new Op(this, opPointer);
-  }
-
-  private native long mkOp(long pointer, int kindValue, int[] args);
-
-  /* .................................................................... */
-  /* Create Constants                                                     */
-  /* .................................................................... */
-
-  /**
-   * Create a Boolean true constant.
-   * @return the true constant
-   */
-  public Term mkTrue()
-  {
-    long termPointer = mkTrue(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkTrue(long pointer);
-  /**
-   * Create a Boolean false constant.
-   * @return the false constant
-   */
-  public Term mkFalse()
-  {
-    long termPointer = mkFalse(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkFalse(long pointer);
-  /**
-   * Create a Boolean constant.
-   * @return the Boolean constant
-   * @param val the value of the constant
-   */
-  public Term mkBoolean(boolean val)
-  {
-    long termPointer = mkBoolean(pointer, val);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkBoolean(long pointer, boolean val);
-  /**
-   * Create a constant representing the number Pi.
-   * @return a constant representing Pi
-   */
-  public Term mkPi()
-  {
-    long termPointer = mkPi(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkPi(long pointer);
-  /**
-   * Create an integer constant from a string.
-   * @param s the string representation of the constant, may represent an
-   *          integer (e.g., "123").
-   * @return a constant of sort Integer assuming 's' represents an integer)
-   */
-  public Term mkInteger(String s) throws CVC5ApiException
-  {
-    long termPointer = mkInteger(pointer, s);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkInteger(long pointer, String s) throws CVC5ApiException;
-
-  /**
-   * Create an integer constant from a c++ int.
-   * @param val the value of the constant
-   * @return a constant of sort Integer
-   */
-  public Term mkInteger(long val)
-  {
-    long termPointer = mkInteger(pointer, val);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkInteger(long pointer, long val);
-  /**
-   * Create a real constant from a string.
-   * @param s the string representation of the constant, may represent an
-   *          integer (e.g., "123") or real constant (e.g., "12.34" or
-   * "12/34").
-   * @return a constant of sort Real
-   */
-  public Term mkReal(String s) throws CVC5ApiException
-  {
-    long termPointer = mkReal(pointer, s);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkReal(long pointer, String s) throws CVC5ApiException;
-  /**
-   * Create a real constant from an integer.
-   * @param val the value of the constant
-   * @return a constant of sort Integer
-   */
-  public Term mkReal(long val)
-  {
-    long termPointer = mkRealValue(pointer, val);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkRealValue(long pointer, long val);
-  /**
-   * Create a real constant from a rational.
-   * @param num the value of the numerator
-   * @param den the value of the denominator
-   * @return a constant of sort Real
-   */
-  public Term mkReal(long num, long den)
-  {
-    long termPointer = mkReal(pointer, num, den);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkReal(long pointer, long num, long den);
-
-  /**
-   * Create a regular expression empty term.
-   * @return the empty term
-   */
-  public Term mkRegexpEmpty()
-  {
-    long termPointer = mkRegexpEmpty(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkRegexpEmpty(long pointer);
-
-  /**
-   * Create a regular expression sigma term.
-   * @return the sigma term
-   */
-  public Term mkRegexpSigma()
-  {
-    long termPointer = mkRegexpSigma(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkRegexpSigma(long pointer);
-
-  /**
-   * Create a constant representing an empty set of the given sort.
-   * @param sort the sort of the set elements.
-   * @return the empty set constant
-   */
-  public Term mkEmptySet(Sort sort)
-  {
-    long termPointer = mkEmptySet(pointer, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkEmptySet(long pointer, long sortPointer);
-  /**
-   * Create a constant representing an empty bag of the given sort.
-   * @param sort the sort of the bag elements.
-   * @return the empty bag constant
-   */
-  public Term mkEmptyBag(Sort sort)
-  {
-    long termPointer = mkEmptyBag(pointer, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkEmptyBag(long pointer, long sortPointer);
-
-  /**
-   * Create a separation logic empty term.
-   * @return the separation logic empty term
-   */
-  public Term mkSepEmp()
-  {
-    long termPointer = mkSepEmp(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkSepEmp(long pointer);
-
-  /**
-   * Create a separation logic nil term.
-   * @param sort the sort of the nil term
-   * @return the separation logic nil term
-   */
-  public Term mkSepNil(Sort sort)
-  {
-    long termPointer = mkSepNil(pointer, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkSepNil(long pointer, long sortPointer);
-
-  /**
-   * Create a String constant.
-   * @param s the string this constant represents
-   * @return the String constant
-   */
-  public Term mkString(String s)
-  {
-    return mkString(s, false);
-  }
-
-  /**
-   * Create a String constant.
-   * @param s the string this constant represents
-   * @param useEscSequences determines whether escape sequences in `s`
-   * should be converted to the corresponding unicode character
-   * @return the String constant
-   */
-  public Term mkString(String s, boolean useEscSequences)
-  {
-    // TODO: review unicode
-    long termPointer = mkString(pointer, s, useEscSequences);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkString(long pointer, String s, boolean useEscSequences);
-
-  /**
-   * Create a String constant.
-   * @param s a list of unsigned (unicode) values this constant represents
-   *     as
-   * string
-   * @return the String constant
-   */
-  public Term mkString(int[] s) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(s, "s");
-    long termPointer = mkString(pointer, s);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkString(long pointer, int[] s);
-
-  /**
-   * Create an empty sequence of the given element sort.
-   * @param sort The element sort of the sequence.
-   * @return the empty sequence with given element sort.
-   */
-  public Term mkEmptySequence(Sort sort)
-  {
-    long termPointer = mkEmptySequence(pointer, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkEmptySequence(long pointer, long sortPointer);
-
-  /**
-   * Create a universe set of the given sort.
-   * @param sort the sort of the set elements
-   * @return the universe set constant
-   */
-  public Term mkUniverseSet(Sort sort)
-  {
-    long termPointer = mkUniverseSet(pointer, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkUniverseSet(long pointer, long sortPointer);
-
-  /**
-   * Create a bit-vector constant of given size and value = 0.
-   * @param size the bit-width of the bit-vector sort
-   * @return the bit-vector constant
-   */
-  public Term mkBitVector(int size) throws CVC5ApiException
-  {
-    return mkBitVector(size, 0);
-  }
-
-  /**
-   * Create a bit-vector constant of given size and value.
-   *
-   * Note: The given value must fit into a bit-vector of the given size.
-   *
-   * @param size the bit-width of the bit-vector sort
-   * @param val the value of the constant
-   * @return the bit-vector constant
-   */
-  public Term mkBitVector(int size, long val) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(size, "size");
-    Utils.validateUnsigned(val, "val");
-    long termPointer = mkBitVector(pointer, size, val);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkBitVector(long pointer, int size, long val);
-
-  /**
-   * Create a bit-vector constant of a given bit-width from a given string of
-   * base 2, 10 or 16.
-   *
-   * Note: The given value must fit into a bit-vector of the given size.
-   *
-   * @param size the bit-width of the constant
-   * @param s the string representation of the constant
-   * @param base the base of the string representation (2, 10, or 16)
-   * @return the bit-vector constant
-   */
-  public Term mkBitVector(int size, String s, int base) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(size, "size");
-    Utils.validateUnsigned(base, "base");
-    long termPointer = mkBitVector(pointer, size, s, base);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkBitVector(long pointer, int size, String s, int base);
-
-  /**
-   * Create a constant array with the provided constant value stored at
-   * every index
-   * @param sort the sort of the constant array (must be an array sort)
-   * @param val the constant value to store (must match the sort's element
-   *     sort)
-   * @return the constant array term
-   */
-  public Term mkConstArray(Sort sort, Term val)
-  {
-    long termPointer = mkConstArray(pointer, sort.getPointer(), val.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkConstArray(long pointer, long sortPointer, long valPointer);
-  /**
-   * Create a positive infinity floating-point constant.
-   * @param exp Number of bits in the exponent
-   * @param sig Number of bits in the significand
-   * @return the floating-point constant
-   */
-  public Term mkPosInf(int exp, int sig) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long termPointer = mkPosInf(pointer, exp, sig);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkPosInf(long pointer, int exp, int sig);
-  /**
-   * Create a negative infinity floating-point constant.
-   * @param exp Number of bits in the exponent
-   * @param sig Number of bits in the significand
-   * @return the floating-point constant
-   */
-  public Term mkNegInf(int exp, int sig) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long termPointer = mkNegInf(pointer, exp, sig);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkNegInf(long pointer, int exp, int sig);
-  /**
-   * Create a not-a-number (NaN) floating-point constant.
-   * @param exp Number of bits in the exponent
-   * @param sig Number of bits in the significand
-   * @return the floating-point constant
-   */
-  public Term mkNaN(int exp, int sig) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long termPointer = mkNaN(pointer, exp, sig);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkNaN(long pointer, int exp, int sig);
-
-  /**
-   * Create a positive zero (+0.0) floating-point constant.
-   * @param exp Number of bits in the exponent
-   * @param sig Number of bits in the significand
-   * @return the floating-point constant
-   */
-  public Term mkPosZero(int exp, int sig) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long termPointer = mkPosZero(pointer, exp, sig);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkPosZero(long pointer, int exp, int sig);
-
-  /**
-   * Create a negative zero (-0.0) floating-point constant.
-   * @param exp Number of bits in the exponent
-   * @param sig Number of bits in the significand
-   * @return the floating-point constant
-   */
-  public Term mkNegZero(int exp, int sig) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long termPointer = mkNegZero(pointer, exp, sig);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkNegZero(long pointer, int exp, int sig);
-
-  /**
-   * Create a roundingmode constant.
-   * @param rm the floating point rounding mode this constant represents
-   */
-  public Term mkRoundingMode(RoundingMode rm)
-  {
-    long termPointer = mkRoundingMode(pointer, rm.getValue());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkRoundingMode(long pointer, int rm);
-
-  /**
-   * Create uninterpreted constant.
-   * @param sort Sort of the constant
-   * @param index Index of the constant
-   */
-  public Term mkUninterpretedConst(Sort sort, int index) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(index, "index");
-    long termPointer = mkUninterpretedConst(pointer, sort.getPointer(), index);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkUninterpretedConst(long pointer, long sortPointer, int index);
-
-  /**
-   * Create an abstract value constant.
-   * @param index Index of the abstract value
-   */
-  public Term mkAbstractValue(String index)
-  {
-    long termPointer = mkAbstractValue(pointer, index);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkAbstractValue(long pointer, String index);
-
-  /**
-   * Create an abstract value constant.
-   * @param index Index of the abstract value
-   */
-  public Term mkAbstractValue(long index) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(index, "index");
-    long termPointer = mkAbstractValue(pointer, index);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkAbstractValue(long pointer, long index);
-
-  /**
-   * Create a floating-point constant.
-   * @param exp Size of the exponent
-   * @param sig Size of the significand
-   * @param val Value of the floating-point constant as a bit-vector term
-   */
-  public Term mkFloatingPoint(int exp, int sig, Term val) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(exp, "exp");
-    Utils.validateUnsigned(sig, "sig");
-    long termPointer = mkFloatingPoint(pointer, exp, sig, val.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkFloatingPoint(long pointer, int exp, int sig, long valPointer);
-
-  /* .................................................................... */
-  /* Create Variables                                                     */
-  /* .................................................................... */
-
-  /**
-   * Create (first-order) constant (0-arity function symbol).
-   * SMT-LIB:
-   * {@code
-   *   ( declare-const <symbol> <sort> )
-   *   ( declare-fun <symbol> ( ) <sort> )
-   * }
-   *
-   * @param sort the sort of the constant
-   * @param symbol the name of the constant
-   * @return the first-order constant
-   */
-  public Term mkConst(Sort sort, String symbol)
-  {
-    long termPointer = mkConst(pointer, sort.getPointer(), symbol);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkConst(long pointer, long sortPointer, String symbol);
-
-  /**
-   * Create (first-order) constant (0-arity function symbol), with a default
-   * symbol name.
-   *
-   * @param sort the sort of the constant
-   * @return the first-order constant
-   */
-  public Term mkConst(Sort sort)
-  {
-    long termPointer = mkConst(pointer, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long mkConst(long pointer, long sortPointer);
-
-  /**
-   * Create a bound variable to be used in a binder (i.e. a quantifier, a
-   * lambda, or a witness binder).
-   * @param sort the sort of the variable
-   * @return the variable
-   */
-  public Term mkVar(Sort sort)
-  {
-    return mkVar(sort, "");
-  }
-
-  /**
-   * Create a bound variable to be used in a binder (i.e. a quantifier, a
-   * lambda, or a witness binder).
-   * @param sort the sort of the variable
-   * @param symbol the name of the variable
-   * @return the variable
-   */
-  public Term mkVar(Sort sort, String symbol)
-  {
-    long termPointer = mkVar(pointer, sort.getPointer(), symbol);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkVar(long pointer, long sortPointer, String symbol);
-
-  /* .................................................................... */
-  /* Create datatype constructor declarations                             */
-  /* .................................................................... */
-
-  public DatatypeConstructorDecl mkDatatypeConstructorDecl(String name)
-  {
-    long declPointer = mkDatatypeConstructorDecl(pointer, name);
-    return new DatatypeConstructorDecl(this, declPointer);
-  }
-
-  private native long mkDatatypeConstructorDecl(long pointer, String name);
-
-  /* .................................................................... */
-  /* Create datatype declarations                                         */
-  /* .................................................................... */
-
-  /**
-   * Create a datatype declaration.
-   * @param name the name of the datatype
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name)
-  {
-    return mkDatatypeDecl(name, false);
-  }
-
-  /**
-   * Create a datatype declaration.
-   * @param name the name of the datatype
-   * @param isCoDatatype true if a codatatype is to be constructed
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name, boolean isCoDatatype)
-  {
-    long declPointer = mkDatatypeDecl(pointer, name, isCoDatatype);
-    return new DatatypeDecl(this, declPointer);
-  }
-
-  private native long mkDatatypeDecl(long pointer, String name, boolean isCoDatatype);
-
-  /**
-   * Create a datatype declaration.
-   * Create sorts parameter with Solver::mkParamSort().
-   * @param name the name of the datatype
-   * @param param the sort parameter
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name, Sort param)
-  {
-    return mkDatatypeDecl(name, param, false);
-  }
-
-  /**
-   * Create a datatype declaration.
-   * Create sorts parameter with Solver::mkParamSort().
-   * @param name the name of the datatype
-   * @param param the sort parameter
-   * @param isCoDatatype true if a codatatype is to be constructed
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name, Sort param, boolean isCoDatatype)
-  {
-    long declPointer = mkDatatypeDecl(pointer, name, param.getPointer(), isCoDatatype);
-    return new DatatypeDecl(this, declPointer);
-  }
-
-  private native long mkDatatypeDecl(
-      long pointer, String name, long paramPointer, boolean isCoDatatype);
-
-  /**
-   * Create a datatype declaration.
-   * Create sorts parameter with Solver::mkParamSort().
-   * @param name the name of the datatype
-   * @param params a list of sort parameters
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name, List<Sort> params)
-  {
-    return mkDatatypeDecl(name, params.toArray(new Sort[0]));
-  }
-
-  /**
-   * Create a datatype declaration.
-   * Create sorts parameter with Solver::mkParamSort().
-   * @param name the name of the datatype
-   * @param params a list of sort parameters
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name, Sort[] params)
-  {
-    return mkDatatypeDecl(name, params, false);
-  }
-
-  /**
-   * Create a datatype declaration.
-   * Create sorts parameter with Solver::mkParamSort().
-   * @param name the name of the datatype
-   * @param params a list of sort parameters
-   * @param isCoDatatype true if a codatatype is to be constructed
-   * @return the DatatypeDecl
-   */
-  public DatatypeDecl mkDatatypeDecl(String name, Sort[] params, boolean isCoDatatype)
-  {
-    long[] paramPointers = Utils.getPointers(params);
-    long declPointer = mkDatatypeDecl(pointer, name, paramPointers, isCoDatatype);
-    return new DatatypeDecl(this, declPointer);
-  }
-
-  private native long mkDatatypeDecl(
-      long pointer, String name, long[] paramPointers, boolean isCoDatatype);
-
-  /* .................................................................... */
-  /* Formula Handling                                                     */
-  /* .................................................................... */
-
-  /**
-   * Simplify a formula without doing "much" work.  Does not involve
-   * the SAT Engine in the simplification, but uses the current
-   * definitions, assertions, and the current partial model, if one
-   * has been constructed.  It also involves theory normalization.
-   * @param t the formula to simplify
-   * @return the simplified formula
-   */
-  public Term simplify(Term t)
-  {
-    long termPointer = simplify(pointer, t.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long simplify(long pointer, long termPointer);
-
-  /**
-   * Assert a formula.
-   * SMT-LIB:
-   * {@code
-   *   ( assert <term> )
-   * }
-   * @param term the formula to assert
-   */
-  public void assertFormula(Term term)
-  {
-    assertFormula(pointer, term.getPointer());
-  }
-
-  private native void assertFormula(long pointer, long termPointer);
-
-  /**
-   * Check satisfiability.
-   * SMT-LIB:
-   * {@code
-   *   ( check-sat )
-   * }
-   * @return the result of the satisfiability check.
-   */
-  public Result checkSat()
-  {
-    long resultPointer = checkSat(pointer);
-    return new Result(this, resultPointer);
-  }
-
-  private native long checkSat(long pointer);
-  /**
-   * Check satisfiability assuming the given formula.
-   * SMT-LIB:
-   * {@code
-   *   ( check-sat-assuming ( <prop_literal> ) )
-   * }
-   * @param assumption the formula to assume
-   * @return the result of the satisfiability check.
-   */
-  public Result checkSatAssuming(Term assumption)
-  {
-    long resultPointer = checkSatAssuming(pointer, assumption.getPointer());
-    return new Result(this, resultPointer);
-  }
-
-  private native long checkSatAssuming(long pointer, long assumptionPointer);
-
-  /**
-   * Check satisfiability assuming the given formulas.
-   * SMT-LIB:
-   * {@code
-   *   ( check-sat-assuming ( <prop_literal>+ ) )
-   * }
-   * @param assumptions the formulas to assume
-   * @return the result of the satisfiability check.
-   */
-  public Result checkSatAssuming(Term[] assumptions)
-  {
-    long[] pointers = Utils.getPointers(assumptions);
-    long resultPointer = checkSatAssuming(pointer, pointers);
-    return new Result(this, resultPointer);
-  }
-
-  private native long checkSatAssuming(long pointer, long[] assumptionPointers);
-
-  /**
-   * Check entailment of the given formula w.r.t. the current set of assertions.
-   * @param term the formula to check entailment for
-   * @return the result of the entailment check.
-   */
-  public Result checkEntailed(Term term)
-  {
-    long resultPointer = checkEntailed(pointer, term.getPointer());
-    return new Result(this, resultPointer);
-  }
-
-  private native long checkEntailed(long pointer, long termPointer);
-
-  /**
-   * Check entailment of the given set of given formulas w.r.t. the current
-   * set of assertions.
-   * @param terms the terms to check entailment for
-   * @return the result of the entailmentcheck.
-   */
-  public Result checkEntailed(Term[] terms)
-  {
-    long[] pointers = Utils.getPointers(terms);
-    long resultPointer = checkEntailed(pointer, pointers);
-    return new Result(this, resultPointer);
-  }
-
-  private native long checkEntailed(long pointer, long[] termPointers);
-
-  /**
-   * Create datatype sort.
-   * SMT-LIB:
-   * {@code
-   *   ( declare-datatype <symbol> <datatype_decl> )
-   * }
-   * @param symbol the name of the datatype sort
-   * @param ctors the constructor declarations of the datatype sort
-   * @return the datatype sort
-   */
-  public Sort declareDatatype(String symbol, DatatypeConstructorDecl[] ctors)
-  {
-    long[] pointers = Utils.getPointers(ctors);
-    long sortPointer = declareDatatype(pointer, symbol, pointers);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long declareDatatype(long pointer, String symbol, long[] declPointers);
-
-  /**
-   * Declare n-ary function symbol.
-   * SMT-LIB:
-   * {@code
-   *   ( declare-fun <symbol> ( <sort>* ) <sort> )
-   * }
-   * @param symbol the name of the function
-   * @param sorts the sorts of the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @return the function
-   */
-  public Term declareFun(String symbol, Sort[] sorts, Sort sort)
-  {
-    long[] sortPointers = Utils.getPointers(sorts);
-    long termPointer = declareFun(pointer, symbol, sortPointers, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long declareFun(
-      long pointer, String symbol, long[] sortPointers, long sortPointer);
-
-  /**
-   * Declare uninterpreted sort.
-   * SMT-LIB:
-   * {@code
-   *   ( declare-sort <symbol> <numeral> )
-   * }
-   * @param symbol the name of the sort
-   * @param arity the arity of the sort
-   * @return the sort
-   */
-  public Sort declareSort(String symbol, int arity) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(arity, "arity");
-    long sortPointer = declareSort(pointer, symbol, arity);
-    return new Sort(this, sortPointer);
-  }
-
-  private native long declareSort(long pointer, String symbol, int arity);
-
-  /**
-   * Define n-ary function in the current context.
-   * SMT-LIB:
-   * {@code
-   *   ( define-fun <function_def> )
-   * }
-   * @param symbol the name of the function
-   * @param boundVars the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @param term the function body
-   * @return the function
-   */
-  public Term defineFun(String symbol, Term[] boundVars, Sort sort, Term term)
-  {
-    return defineFun(symbol, boundVars, sort, term, false);
-  }
-
-  /**
-   * Define n-ary function.
-   * SMT-LIB:
-   * {@code
-   *   ( define-fun <function_def> )
-   * }
-   * @param symbol the name of the function
-   * @param boundVars the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @param term the function body
-   * @param global determines whether this definition is global (i.e. persists
-   *               when popping the context)
-   * @return the function
-   */
-  public Term defineFun(String symbol, Term[] boundVars, Sort sort, Term term, boolean global)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer =
-        defineFun(pointer, symbol, boundVarPointers, sort.getPointer(), term.getPointer(), global);
-    return new Term(this, termPointer);
-  }
-
-  private native long defineFun(long pointer,
-      String symbol,
-      long[] boundVarPointers,
-      long sortPointer,
-      long termPointer,
-      boolean global);
-
-  /**
-   * Define n-ary function in the current context.
-   * SMT-LIB:
-   * {@code
-   * ( define-fun <function_def> )
-   * }
-   * Create parameter 'fun' with mkConst().
-   * @param fun the sorted function
-   * @param boundVars the parameters to this function
-   * @param term the function body
-   * @return the function
-   */
-  public Term defineFun(Term fun, Term[] boundVars, Term term)
-  {
-    return defineFun(fun, boundVars, term, false);
-  }
-  /**
-   * Define n-ary function.
-   * SMT-LIB:
-   * {@code
-   * ( define-fun <function_def> )
-   * }
-   * Create parameter 'fun' with mkConst().
-   * @param fun the sorted function
-   * @param boundVars the parameters to this function
-   * @param term the function body
-   * @param global determines whether this definition is global (i.e. persists
-   *               when popping the context)
-   * @return the function
-   */
-  public Term defineFun(Term fun, Term[] boundVars, Term term, boolean global)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer =
-        defineFun(pointer, fun.getPointer(), boundVarPointers, term.getPointer(), global);
-    return new Term(this, termPointer);
-  }
-
-  private native long defineFun(
-      long pointer, long funPointer, long[] boundVarPointers, long termPointer, boolean global);
-
-  /**
-   * Define recursive function in the current context.
-   * SMT-LIB:
-   * {@code
-   * ( define-fun-rec <function_def> )
-   * }
-   * @param symbol the name of the function
-   * @param boundVars the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @param term the function body
-   * @return the function
-   */
-  public Term defineFunRec(String symbol, Term[] boundVars, Sort sort, Term term)
-  {
-    return defineFunRec(symbol, boundVars, sort, term, false);
-  }
-
-  /**
-   * Define recursive function.
-   * SMT-LIB:
-   * {@code
-   * ( define-fun-rec <function_def> )
-   * }
-   * @param symbol the name of the function
-   * @param boundVars the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @param term the function body
-   * @param global determines whether this definition is global (i.e. persists
-   *               when popping the context)
-   * @return the function
-   */
-  public Term defineFunRec(String symbol, Term[] boundVars, Sort sort, Term term, boolean global)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer = defineFunRec(
-        pointer, symbol, boundVarPointers, sort.getPointer(), term.getPointer(), global);
-    return new Term(this, termPointer);
-  }
-
-  private native long defineFunRec(long pointer,
-      String symbol,
-      long[] boundVarPointers,
-      long sortPointer,
-      long termPointer,
-      boolean global);
-
-  /**
-   * Define recursive function in the current context.
-   * SMT-LIB:
-   * {@code
-   * ( define-fun-rec <function_def> )
-   * }
-   * Create parameter 'fun' with mkConst().
-   * @param fun the sorted function
-   * @param boundVars the parameters to this function
-   * @param term the function body
-   * @return the function
-   */
-
-  public Term defineFunRec(Term fun, Term[] boundVars, Term term)
-  {
-    return defineFunRec(fun, boundVars, term, false);
-  }
-
-  /**
-   * Define recursive function.
-   * SMT-LIB:
-   * {@code
-   * ( define-fun-rec <function_def> )
-   * }
-   * Create parameter 'fun' with mkConst().
-   * @param fun the sorted function
-   * @param boundVars the parameters to this function
-   * @param term the function body
-   * @param global determines whether this definition is global (i.e. persists
-   *               when popping the context)
-   * @return the function
-   */
-  public Term defineFunRec(Term fun, Term[] boundVars, Term term, boolean global)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer =
-        defineFunRec(pointer, fun.getPointer(), boundVarPointers, term.getPointer(), global);
-    return new Term(this, termPointer);
-  }
-
-  private native long defineFunRec(
-      long pointer, long funPointer, long[] boundVarPointers, long termPointer, boolean global);
-
-  /**
-   * Define recursive functions in the current context.
-   * SMT-LIB:
-   * {@code
-   *   ( define-funs-rec ( <function_decl>^{n+1} ) ( <term>^{n+1} ) )
-   * }
-   * Create elements of parameter 'funs' with mkConst().
-   * @param funs the sorted functions
-   * @param boundVars the list of parameters to the functions
-   * @param terms the list of function bodies of the functions
-   */
-  public void defineFunsRec(Term[] funs, Term[][] boundVars, Term[] terms)
-  {
-    defineFunsRec(funs, boundVars, terms, false);
-  }
-  /**
-   * Define recursive functions.
-   * SMT-LIB:
-   * {@code
-   *   ( define-funs-rec ( <function_decl>^{n+1} ) ( <term>^{n+1} ) )
-   * }
-   * Create elements of parameter 'funs' with mkConst().
-   * @param funs the sorted functions
-   * @param boundVars the list of parameters to the functions
-   * @param terms the list of function bodies of the functions
-   * @param global determines whether this definition is global (i.e. persists
-   *               when popping the context)
-   */
-  public void defineFunsRec(Term[] funs, Term[][] boundVars, Term[] terms, boolean global)
-  {
-    long[] funPointers = Utils.getPointers(funs);
-    long[][] boundVarPointers = Utils.getPointers(boundVars);
-    long[] termPointers = Utils.getPointers(terms);
-    defineFunsRec(pointer, funPointers, boundVarPointers, termPointers, global);
-  }
-
-  private native void defineFunsRec(long pointer,
-      long[] funPointers,
-      long[][] boundVarPointers,
-      long[] termPointers,
-      boolean global);
-
-  /**
-   * Echo a given string to the given output stream.
-   * SMT-LIB:
-   * {@code
-   * ( echo <std::string> )
-   * }
-   * @param out the output stream
-   * @param str the string to echo
-   */
-  // TODO: void echo(std::ostream& out, String  str)
-
-  /**
-   * Get the list of asserted formulas.
-   * SMT-LIB:
-   * {@code
-   * ( get-assertions )
-   * }
-   * @return the list of asserted formulas
-   */
-  public Term[] getAssertions()
-  {
-    long[] retPointers = getAssertions(pointer);
-    return Utils.getTerms(this, retPointers);
-  }
-
-  private native long[] getAssertions(long pointer);
-
-  /**
-   * Get info from the solver.
-   * SMT-LIB: {@code ( get-info <info_flag> ) }
-   * @return the info
-   */
-  public String getInfo(String flag)
-  {
-    return getInfo(pointer, flag);
-  }
-
-  private native String getInfo(long pointer, String flag);
-
-  /**
-   * Get the value of a given option.
-   * SMT-LIB:
-   * {@code
-   * ( get-option <keyword> )
-   * }
-   * @param option the option for which the value is queried
-   * @return a string representation of the option value
-   */
-  public String getOption(String option)
-  {
-    return getOption(pointer, option);
-  }
-
-  private native String getOption(long pointer, String option);
-
-  /**
-   * Get all option names that can be used with `setOption`, `getOption` and
-   * `getOptionInfo`.
-   * @return all option names
-   */
-  public String[] getOptionNames()
-  {
-    return getOptionNames(pointer);
-  }
-
-  private native String[] getOptionNames(long pointer);
-
-  /**
-   * Get some information about the given option. Check the `OptionInfo` class
-   * for more details on which information is available.
-   * @return information about the given option
-   */
-  public OptionInfo getOptionInfo(String option)
-  {
-    long optionPointer = getOptionInfo(pointer, option);
-    return new OptionInfo(this, optionPointer);
-  }
-
-  private native long getOptionInfo(long pointer, String option);
-
-  /**
-   * Get the set of unsat ("failed") assumptions.
-   * SMT-LIB:
-   * {@code
-   * ( get-unsat-assumptions )
-   * }
-   * Requires to enable option 'produce-unsat-assumptions'.
-   * @return the set of unsat assumptions.
-   */
-  public Term[] getUnsatAssumptions()
-  {
-    long[] retPointers = getUnsatAssumptions(pointer);
-    return Utils.getTerms(this, retPointers);
-  }
-
-  private native long[] getUnsatAssumptions(long pointer);
-
-  /**
-   * Get the unsatisfiable core.
-   * SMT-LIB:
-   * {@code
-   * ( get-unsat-core )
-   * }
-   * Requires to enable option 'produce-unsat-cores'.
-   * @return a set of terms representing the unsatisfiable core
-   */
-  public Term[] getUnsatCore()
-  {
-    long[] retPointers = getUnsatCore(pointer);
-    return Utils.getTerms(this, retPointers);
-  }
-
-  private native long[] getUnsatCore(long pointer);
-
-  /**
-   * Get a difficulty estimate for an asserted formula. This method is
-   * intended to be called immediately after any response to a checkSat.
-   *
-   * @return a map from (a subset of) the input assertions to a real value that
-   * is an estimate of how difficult each assertion was to solve. Unmentioned
-   * assertions can be assumed to have zero difficulty.
-   */
-  public Map<Term, Term> getDifficulty()
-  {
-    Map<Long, Long> map = getDifficulty(pointer);
-    Map<Term, Term> ret = new HashMap<>();
-    for (Map.Entry<Long, Long> entry : map.entrySet())
-    {
-      Term key = new Term(this, entry.getKey());
-      Term value = new Term(this, entry.getValue());
-      ret.put(key, value);
-    }
-    return ret;
-  }
-
-  private native Map<Long, Long> getDifficulty(long pointer);
-
-  /**
-   * Get the refutation proof
-   * SMT-LIB:
-   * {@code
-   * ( get-proof )
-   * }
-   * Requires to enable option 'produce-proofs'.
-   * @return a string representing the proof, according to the value of
-   * proof-format-mode.
-   */
-  public String getProof()
-  {
-    return getProof(pointer);
-  }
-
-  private native String getProof(long pointer);
-
-  /**
-   * Get the value of the given term in the current model.
-   * SMT-LIB:
-   * {@code
-   * ( get-value ( <term> ) )
-   * }
-   * @param term the term for which the value is queried
-   * @return the value of the given term
-   */
-  public Term getValue(Term term)
-  {
-    long termPointer = getValue(pointer, term.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long getValue(long pointer, long termPointer);
-
-  /**
-   * Get the values of the given terms in the current model.
-   * SMT-LIB:
-   * {@code
-   * ( get-value ( <term>+ ) )
-   * }
-   * @param terms the terms for which the value is queried
-   * @return the values of the given terms
-   */
-  public Term[] getValue(Term[] terms)
-  {
-    long[] pointers = Utils.getPointers(terms);
-    long[] retPointers = getValue(pointer, pointers);
-    return Utils.getTerms(this, retPointers);
-  }
-
-  private native long[] getValue(long pointer, long[] termPointers);
-
-  /**
-   * Get the domain elements of uninterpreted sort s in the current model. The
-   * current model interprets s as the finite sort whose domain elements are
-   * given in the return value of this method.
-   *
-   * @param s The uninterpreted sort in question
-   * @return the domain elements of s in the current model
-   */
-  public Term[] getModelDomainElements(Sort s)
-  {
-    long[] pointers = getModelDomainElements(pointer, s.getPointer());
-    return Utils.getTerms(this, pointers);
-  }
-
-  private native long[] getModelDomainElements(long pointer, long sortPointer);
-
-  /**
-   * This returns false if the model value of free constant v was not essential
-   * for showing the satisfiability of the last call to checkSat using the
-   * current model. This method will only return false (for any v) if
-   * the model-cores option has been set.
-   *
-   * @param v The term in question
-   * @return true if v is a model core symbol
-   */
-  public boolean isModelCoreSymbol(Term v)
-  {
-    return isModelCoreSymbol(pointer, v.getPointer());
-  }
-
-  private native boolean isModelCoreSymbol(long pointer, long termPointer);
-
-  /**
-   * Get the model
-   * SMT-LIB:
-   * {@code
-   * ( get-model )
-   * }
-   * Requires to enable option 'produce-models'.
-   * @param sorts The list of uninterpreted sorts that should be printed in the
-   * model.
-   * @param vars The list of free constants that should be printed in the
-   * model. A subset of these may be printed based on isModelCoreSymbol.
-   * @return a string representing the model.
-   */
-  public String getModel(Sort[] sorts, Term[] vars)
-  {
-    long[] sortPointers = Utils.getPointers(sorts);
-    long[] varPointers = Utils.getPointers(vars);
-    return getModel(pointer, sortPointers, varPointers);
-  }
-
-  private native String getModel(long pointer, long[] sortPointers, long[] varPointers);
-
-  /**
-   * Do quantifier elimination.
-   * SMT-LIB:
-   * {@code
-   * ( get-qe <q> )
-   * }
-   * Requires a logic that supports quantifier elimination. Currently, the only
-   * logics supported by quantifier elimination is LRA and LIA.
-   * @param q a quantified formula of the form:
-   *   Q x1...xn. P( x1...xn, y1...yn )
-   * where P( x1...xn, y1...yn ) is a quantifier-free formula
-   * @return a formula ret such that, given the current set of formulas A
-   * asserted to this solver:
-   *   - ( A ^ q ) and ( A ^ ret ) are equivalent
-   *   - ret is quantifier-free formula containing only free variables in
-   *     y1...yn.
-   */
-  public Term getQuantifierElimination(Term q)
-  {
-    long termPointer = getQuantifierElimination(pointer, q.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long getQuantifierElimination(long pointer, long qPointer);
-
-  /**
-   * Do partial quantifier elimination, which can be used for incrementally
-   * computing the result of a quantifier elimination.
-   * SMT-LIB:
-   * {@code
-   * ( get-qe-disjunct <q> )
-   * }
-   * Requires a logic that supports quantifier elimination. Currently, the only
-   * logics supported by quantifier elimination is LRA and LIA.
-   * @param q a quantified formula of the form:
-   *   Q x1...xn. P( x1...xn, y1...yn )
-   * where P( x1...xn, y1...yn ) is a quantifier-free formula
-   * @return a formula ret such that, given the current set of formulas A
-   * asserted to this solver:
-   *   - {@code (A ^ q) => (A ^ ret)} if Q is forall or {@code (A ^ ret) => (A ^ q)} if Q is
-   *     exists,
-   *   - ret is quantifier-free formula containing only free variables in
-   *     y1...yn,
-   *   - If Q is exists, let A^Q_n be the formula
-   *       {@code A ^ ~ret^Q_1 ^ ... ^ ~ret^Q_n}
-   *     where for each i=1,...n, formula ret^Q_i is the result of calling
-   *     getQuantifierEliminationDisjunct for q with the set of assertions
-   *     {@code A^Q_{i-1}}. Similarly, if Q is forall, then let {@code A^Q_n} be
-   *       {@code A ^ ret^Q_1 ^ ... ^ ret^Q_n }
-   *     where ret^Q_i is the same as above. In either case, we have
-   *     that ret^Q_j will eventually be true or false, for some finite j.
-   */
-  public Term getQuantifierEliminationDisjunct(Term q)
-  {
-    long termPointer = getQuantifierEliminationDisjunct(pointer, q.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long getQuantifierEliminationDisjunct(long pointer, long qPointer);
-
-  /**
-   * When using separation logic, this sets the location sort and the
-   * datatype sort to the given ones. This method should be invoked exactly
-   * once, before any separation logic constraints are provided.
-   * @param locSort The location sort of the heap
-   * @param dataSort The data sort of the heap
-   */
-  public void declareSeparationHeap(Sort locSort, Sort dataSort)
-  {
-    declareSeparationHeap(pointer, locSort.getPointer(), dataSort.getPointer());
-  }
-
-  private native void declareSeparationHeap(
-      long pointer, long locSortPointer, long dataSortPointer);
-
-  /**
-   * When using separation logic, obtain the term for the heap.
-   * @return The term for the heap
-   */
-  public Term getSeparationHeap()
-  {
-    long termPointer = getSeparationHeap(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long getSeparationHeap(long pointer);
-
-  /**
-   * When using separation logic, obtain the term for nil.
-   * @return The term for nil
-   */
-  public Term getSeparationNilTerm()
-  {
-    long termPointer = getSeparationNilTerm(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long getSeparationNilTerm(long pointer);
-
-  /**
-   * Declare a symbolic pool of terms with the given initial value.
-   * SMT-LIB:
-   * {@code
-   * ( declare-pool <symbol> <sort> ( <term>* ) )
-   * }
-   * @param symbol The name of the pool
-   * @param sort The sort of the elements of the pool.
-   * @param initValue The initial value of the pool
-   */
-  public Term declarePool(String symbol, Sort sort, Term[] initValue)
-  {
-    long[] termPointers = Utils.getPointers(initValue);
-    long termPointer = declarePool(pointer, symbol, sort.getPointer(), termPointers);
-    return new Term(this, termPointer);
-  }
-
-  private native long declarePool(
-      long pointer, String symbol, long sortPointer, long[] termPointers);
-
-  /**
-   * Pop a level from the assertion stack.
-   * SMT-LIB:
-   * {@code
-   * ( pop <numeral> )
-   * }
-   */
-  public void pop() throws CVC5ApiException
-  {
-    pop(1);
-  }
-
-  /**
-   * Pop (a) level(s) from the assertion stack.
-   * SMT-LIB:
-   * {@code
-   * ( pop <numeral> )
-   * }
-   * @param nscopes the number of levels to pop
-   */
-  public void pop(int nscopes) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(nscopes, "nscopes");
-    pop(pointer, nscopes);
-  }
-
-  private native void pop(long pointer, int nscopes);
-
-  /**
-   * Get an interpolant
-   * SMT-LIB:
-   * {@code
-   * ( get-interpol <conj> )
-   * }
-   * Requires to enable option 'produce-interpols'.
-   * @param conj the conjecture term
-   * @param output a Term I such that {@code A->I} and {@code I->B} are valid, where A is the
-   *        current set of assertions and B is given in the input by conj.
-   * @return true if it gets I successfully, false otherwise.
-   */
-  public boolean getInterpolant(Term conj, Term output)
-  {
-    return getInterpolant(pointer, conj.getPointer(), output.getPointer());
-  }
-
-  private native boolean getInterpolant(long pointer, long conjPointer, long outputPointer);
-
-  /**
-   * Get an interpolant
-   * SMT-LIB:
-   * {@code
-   * ( get-interpol <conj> <g> )
-   * }
-   * Requires to enable option 'produce-interpols'.
-   * @param conj the conjecture term
-   * @param grammar the grammar for the interpolant I
-   * @param output a Term I such that {@code A->I} and {@code I->B} are valid, where A is the
-   *        current set of assertions and B is given in the input by conj.
-   * @return true if it gets I successfully, false otherwise.
-   */
-  public boolean getInterpolant(Term conj, Grammar grammar, Term output)
-  {
-    return getInterpolant(pointer, conj.getPointer(), grammar.getPointer(), output.getPointer());
-  }
-
-  private native boolean getInterpolant(
-      long pointer, long conjPointer, long grammarPointer, long outputPointer);
-
-  /**
-   * Get an abduct.
-   * SMT-LIB:
-   * {@code
-   * ( get-abduct <conj> )
-   * }
-   * Requires enabling option 'produce-abducts'
-   * @param conj the conjecture term
-   * @param output a term C such that A^C is satisfiable, and A^~B^C is
-   *        unsatisfiable, where A is the current set of assertions and B is
-   *        given in the input by conj
-   * @return true if it gets C successfully, false otherwise
-   */
-  public boolean getAbduct(Term conj, Term output)
-  {
-    return getAbduct(pointer, conj.getPointer(), output.getPointer());
-  }
-
-  private native boolean getAbduct(long pointer, long conjPointer, long outputPointer);
-  /**
-   * Get an abduct.
-   * SMT-LIB:
-   * {@code
-   * ( get-abduct <conj> <g> )
-   * }
-   * Requires enabling option 'produce-abducts'
-   * @param conj the conjecture term
-   * @param grammar the grammar for the abduct C
-   * @param output a term C such that A^C is satisfiable, and A^~B^C is
-   *        unsatisfiable, where A is the current set of assertions and B is
-   *        given in the input by conj
-   * @return true if it gets C successfully, false otherwise
-   */
-  public boolean getAbduct(Term conj, Grammar grammar, Term output)
-  {
-    return getAbduct(pointer, conj.getPointer(), grammar.getPointer(), output.getPointer());
-  }
-
-  private native boolean getAbduct(
-      long pointer, long conjPointer, long grammarPointer, long outputPointer);
-
-  /**
-   * Block the current model. Can be called only if immediately preceded by a
-   * SAT or INVALID query.
-   * SMT-LIB:
-   * {@code
-   * ( block-model )
-   * }
-   * Requires enabling 'produce-models' option and setting 'block-models' option
-   * to a mode other than "none".
-   */
-  public void blockModel()
-  {
-    blockModel(pointer);
-  }
-
-  private native void blockModel(long pointer);
-
-  /**
-   * Block the current model values of (at least) the values in terms. Can be
-   * called only if immediately preceded by a SAT or NOT_ENTAILED query.
-   * SMT-LIB:
-   * {@code
-   * ( block-model-values ( <terms>+ ) )
-   * }
-   * Requires enabling 'produce-models' option and setting 'block-models' option
-   * to a mode other than "none".
-   */
-  public void blockModelValues(Term[] terms)
-  {
-    long[] pointers = Utils.getPointers(terms);
-    blockModelValues(pointer, pointers);
-  }
-
-  private native void blockModelValues(long pointer, long[] termPointers);
-
-  /**
-   * Print all instantiations made by the quantifiers module.
-   * @param out the output stream
-   */
-  // TODO: void printInstantiations(std::ostream& out)
-
-  /**
-   * Push a level to the assertion stack.
-   * SMT-LIB:
-   * {@code
-   * ( push <numeral> )
-   * }
-   */
-  public void push() throws CVC5ApiException
-  {
-    push(1);
-  }
-
-  /**
-   * Push (a) level(s) to the assertion stack.
-   * SMT-LIB:
-   * {@code
-   * ( push <numeral> )
-   * }
-   * @param nscopes the number of levels to push
-   */
-  public void push(int nscopes) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(nscopes, "nscopes");
-    push(pointer, nscopes);
-  }
-
-  private native void push(long pointer, int nscopes);
-
-  /**
-   * Remove all assertions.
-   * SMT-LIB:
-   * {@code
-   * ( reset-assertions )
-   * }
-   */
-  public void resetAssertions()
-  {
-    resetAssertions(pointer);
-  }
-
-  private native void resetAssertions(long pointer);
-
-  /**
-   * Set info.
-   * SMT-LIB:
-   * {@code
-   * ( set-info <attribute> )
-   * }
-   * @param keyword the info flag
-   * @param value the value of the info flag
-   */
-  public void setInfo(String keyword, String value) throws CVC5ApiException
-  {
-    setInfo(pointer, keyword, value);
-  }
-
-  private native void setInfo(long pointer, String keyword, String value) throws CVC5ApiException;
-
-  /**
-   * Set logic.
-   * SMT-LIB:
-   * {@code
-   * ( set-logic <symbol> )
-   * }
-   * @param logic the logic to set
-   */
-  public void setLogic(String logic) throws CVC5ApiException
-  {
-    setLogic(pointer, logic);
-  }
-
-  private native void setLogic(long pointer, String logic) throws CVC5ApiException;
-
-  /**
-   * Set option.
-   * SMT-LIB:
-   * {@code
-   *   ( set-option <option> )
-   * }
-   * @param option the option name
-   * @param value the option value
-   */
-  public void setOption(String option, String value)
-  {
-    setOption(pointer, option, value);
-  }
-
-  private native void setOption(long pointer, String option, String value);
-
-  /**
-   * If needed, convert this term to a given sort. Note that the sort of the
-   * term must be convertible into the target sort. Currently only Int to Real
-   * conversions are supported.
-   * @param t the term
-   * @param s the target sort
-   * @return the term wrapped into a sort conversion if needed
-   */
-  public Term ensureTermSort(Term t, Sort s)
-  {
-    long termPointer = ensureTermSort(pointer, t.getPointer(), s.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long ensureTermSort(long pointer, long termPointer, long sortPointer);
-
-  /**
-   * Append \p symbol to the current list of universal variables.
-   * @param sort the sort of the universal variable
-   * @return the universal variable
-   */
-  public Term mkSygusVar(Sort sort)
-  {
-    return mkSygusVar(sort, "");
-  }
-  /**
-   * Append \p symbol to the current list of universal variables.
-   * SyGuS v2:
-   * {@code
-   *   ( declare-var <symbol> <sort> )
-   * }
-   * @param sort the sort of the universal variable
-   * @param symbol the name of the universal variable
-   * @return the universal variable
-   */
-  public Term mkSygusVar(Sort sort, String symbol)
-  {
-    long termPointer = mkSygusVar(pointer, sort.getPointer(), symbol);
-    return new Term(this, termPointer);
-  }
-
-  private native long mkSygusVar(long pointer, long sortPointer, String symbol);
-
-  /**
-   * Create a Sygus grammar. The first non-terminal is treated as the starting
-   * non-terminal, so the order of non-terminals matters.
-   *
-   * @param boundVars the parameters to corresponding synth-fun/synth-inv
-   * @param ntSymbols the pre-declaration of the non-terminal symbols
-   * @return the grammar
-   */
-  public Grammar mkSygusGrammar(Term[] boundVars, Term[] ntSymbols)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long[] ntSymbolPointers = Utils.getPointers(ntSymbols);
-    long grammarPointer = mkSygusGrammar(pointer, boundVarPointers, ntSymbolPointers);
-    return new Grammar(this, grammarPointer);
-  }
-
-  private native long mkSygusGrammar(
-      long pointer, long[] boundVarPointers, long[] ntSymbolPointers);
-
-  /**
-   * Synthesize n-ary function.
-   * SyGuS v2:
-   * {@code
-   *   ( synth-fun <symbol> ( <boundVars>* ) <sort> )
-   * }
-   * @param symbol the name of the function
-   * @param boundVars the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @return the function
-   */
-  public Term synthFun(String symbol, Term[] boundVars, Sort sort)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer = synthFun(pointer, symbol, boundVarPointers, sort.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long synthFun(
-      long pointer, String symbol, long[] boundVarPointers, long sortPointer);
-
-  /**
-   * Synthesize n-ary function following specified syntactic constraints.
-   * SyGuS v2:
-   * {@code
-   *   ( synth-fun <symbol> ( <boundVars>* ) <sort> <g> )
-   * }
-   * @param symbol the name of the function
-   * @param boundVars the parameters to this function
-   * @param sort the sort of the return value of this function
-   * @param grammar the syntactic constraints
-   * @return the function
-   */
-  public Term synthFun(String symbol, Term[] boundVars, Sort sort, Grammar grammar)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer =
-        synthFun(pointer, symbol, boundVarPointers, sort.getPointer(), grammar.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long synthFun(
-      long pointer, String symbol, long[] boundVarPointers, long sortPointer, long grammarPointer);
-
-  /**
-   * Synthesize invariant.
-   * SyGuS v2:
-   * {@code
-   *   ( synth-inv <symbol> ( <boundVars>* ) )
-   * }
-   * @param symbol the name of the invariant
-   * @param boundVars the parameters to this invariant
-   * @return the invariant
-   */
-  public Term synthInv(String symbol, Term[] boundVars)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer = synthInv(pointer, symbol, boundVarPointers);
-    return new Term(this, termPointer);
-  }
-
-  private native long synthInv(long pointer, String symbol, long[] boundVarPointers);
-
-  /**
-   * Synthesize invariant following specified syntactic constraints.
-   * SyGuS v2:
-   * {@code
-   *   ( synth-inv <symbol> ( <boundVars>* ) <g> )
-   * }
-   * @param symbol the name of the invariant
-   * @param boundVars the parameters to this invariant
-   * @param grammar the syntactic constraints
-   * @return the invariant
-   */
-  public Term synthInv(String symbol, Term[] boundVars, Grammar grammar)
-  {
-    long[] boundVarPointers = Utils.getPointers(boundVars);
-    long termPointer = synthInv(pointer, symbol, boundVarPointers, grammar.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long synthInv(
-      long pointer, String symbol, long[] boundVarPointers, long grammarPointer);
-
-  /**
-   * Add a forumla to the set of Sygus constraints.
-   * SyGuS v2:
-   * {@code
-   *   ( constraint <term> )
-   * }
-   * @param term the formula to add as a constraint
-   */
-  public void addSygusConstraint(Term term)
-  {
-    addSygusConstraint(pointer, term.getPointer());
-  }
-
-  private native void addSygusConstraint(long pointer, long termPointer);
-
-  /**
-   * Add a forumla to the set of Sygus assumptions.
-   * SyGuS v2:
-   * {@code
-   *   ( assume <term> )
-   * }
-   * @param term the formula to add as an assumption
-   */
-  public void addSygusAssume(Term term)
-  {
-    addSygusAssume(pointer, term.getPointer());
-  }
-
-  private native void addSygusAssume(long pointer, long termPointer);
-
-  /**
-   * Add a set of Sygus constraints to the current state that correspond to an
-   * invariant synthesis problem.
-   * SyGuS v2:
-   * {@code
-   *   ( inv-constraint <inv> <pre> <trans> <post> )
-   * }
-   * @param inv the function-to-synthesize
-   * @param pre the pre-condition
-   * @param trans the transition relation
-   * @param post the post-condition
-   */
-  public void addSygusInvConstraint(Term inv, Term pre, Term trans, Term post)
-  {
-    addSygusInvConstraint(
-        pointer, inv.getPointer(), pre.getPointer(), trans.getPointer(), post.getPointer());
-  }
-
-  private native void addSygusInvConstraint(
-      long pointer, long invPointer, long prePointer, long transPointer, long postPointer);
-
-  /**
-   * Try to find a solution for the synthesis conjecture corresponding to the
-   * current list of functions-to-synthesize, universal variables and
-   * constraints.
-   * SyGuS v2:
-   * {@code
-   *   ( check-synth )
-   * }
-   * @return the result of the synthesis conjecture.
-   */
-  public Result checkSynth()
-  {
-    long resultPointer = checkSynth(pointer);
-    return new Result(this, resultPointer);
-  }
-
-  private native long checkSynth(long pointer);
-
-  /**
-   * Get the synthesis solution of the given term. This method should be called
-   * immediately after the solver answers unsat for sygus input.
-   * @param term the term for which the synthesis solution is queried
-   * @return the synthesis solution of the given term
-   */
-  public Term getSynthSolution(Term term)
-  {
-    long termPointer = getSynthSolution(pointer, term.getPointer());
-    return new Term(this, termPointer);
-  }
-
-  private native long getSynthSolution(long pointer, long termPointer);
-
-  /**
-   * Get the synthesis solutions of the given terms. This method should be
-   * called immediately after the solver answers unsat for sygus input.
-   * @param terms the terms for which the synthesis solutions is queried
-   * @return the synthesis solutions of the given terms
-   */
-  public Term[] getSynthSolutions(Term[] terms)
-  {
-    long[] termPointers = Utils.getPointers(terms);
-    long[] retPointers = getSynthSolutions(pointer, termPointers);
-    return Utils.getTerms(this, retPointers);
-  }
-
-  private native long[] getSynthSolutions(long pointer, long[] termPointers);
-
-  /**
-   * Returns a snapshot of the current state of the statistic values of this
-   * solver. The returned object is completely decoupled from the solver and
-   * will not change when the solver is used again.
-   */
-  public Statistics getStatistics()
-  {
-    long statisticsPointer = getStatistics(pointer);
-    return new Statistics(this, statisticsPointer);
-  }
-
-  private native long getStatistics(long pointer);
-
-  /**
-   * @return null term
-   */
-  public Term getNullTerm()
-  {
-    long termPointer = getNullTerm(pointer);
-    return new Term(this, termPointer);
-  }
-
-  private native long getNullTerm(long pointer);
-
-  /**
-   * @return null result
-   */
-  public Result getNullResult()
-  {
-    long resultPointer = getNullResult(pointer);
-    return new Result(this, resultPointer);
-  }
-
-  private native long getNullResult(long pointer);
-
-  /**
-   * @return null op
-   */
-  public Op getNullOp()
-  {
-    long opPointer = getNullOp(pointer);
-    return new Op(this, opPointer);
-  }
-
-  private native long getNullOp(long pointer);
-
-  /**
-   * @return null op
-   */
-  public DatatypeDecl getNullDatatypeDecl()
-  {
-    long declPointer = getNullDatatypeDecl(pointer);
-    return new DatatypeDecl(this, declPointer);
-  }
-
-  private native long getNullDatatypeDecl(long pointer);
-}
diff --git a/src/api/java/cvc5/Sort.java b/src/api/java/cvc5/Sort.java
deleted file mode 100644 (file)
index 434c074..0000000
+++ /dev/null
@@ -1,802 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.util.List;
-
-public class Sort extends AbstractPointer implements Comparable<Sort>
-{
-  // region construction and destruction
-  Sort(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * Comparison for structural equality.
-   * @param s the sort to compare to
-   * @return true if the sorts are equal
-   */
-  @Override public boolean equals(Object s)
-  {
-    if (this == s)
-      return true;
-    if (s == null || getClass() != s.getClass())
-      return false;
-    Sort sort = (Sort) s;
-    if (this.pointer == sort.pointer)
-    {
-      return true;
-    }
-    return equals(pointer, sort.getPointer());
-  }
-
-  private native boolean equals(long pointer1, long pointer2);
-
-  /**
-   * Comparison for ordering on sorts.
-   *
-   * @param s the sort to compare to
-   * @return a negative integer, zero, or a positive integer as this sort
-   * is less than, equal to, or greater than the specified sort.
-   */
-  @Override public int compareTo(Sort s)
-  {
-    return this.compareTo(pointer, s.getPointer());
-  }
-
-  private native int compareTo(long pointer1, long pointer2);
-
-  /**
-   * @return true if this Sort is a null sort.
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * Is this a Boolean sort?
-   * @return true if the sort is a Boolean sort
-   */
-  public boolean isBoolean()
-  {
-    return isBoolean(pointer);
-  }
-
-  private native boolean isBoolean(long pointer);
-
-  /**
-   * Is this a integer sort?
-   * @return true if the sort is a integer sort
-   */
-  public boolean isInteger()
-  {
-    return isInteger(pointer);
-  }
-
-  private native boolean isInteger(long pointer);
-
-  /**
-   * Is this a real sort?
-   * @return true if the sort is a real sort
-   */
-  public boolean isReal()
-  {
-    return isReal(pointer);
-  }
-
-  private native boolean isReal(long pointer);
-
-  /**
-   * Is this a string sort?
-   * @return true if the sort is the string sort
-   */
-  public boolean isString()
-  {
-    return isString(pointer);
-  }
-
-  private native boolean isString(long pointer);
-
-  /**
-   * Is this a regexp sort?
-   * @return true if the sort is the regexp sort
-   */
-  public boolean isRegExp()
-  {
-    return isRegExp(pointer);
-  }
-
-  private native boolean isRegExp(long pointer);
-
-  /**
-   * Is this a rounding mode sort?
-   * @return true if the sort is the rounding mode sort
-   */
-  public boolean isRoundingMode()
-  {
-    return isRoundingMode(pointer);
-  }
-
-  private native boolean isRoundingMode(long pointer);
-
-  /**
-   * Is this a bit-vector sort?
-   * @return true if the sort is a bit-vector sort
-   */
-  public boolean isBitVector()
-  {
-    return isBitVector(pointer);
-  }
-
-  private native boolean isBitVector(long pointer);
-
-  /**
-   * Is this a floating-point sort?
-   * @return true if the sort is a floating-point sort
-   */
-  public boolean isFloatingPoint()
-  {
-    return isFloatingPoint(pointer);
-  }
-
-  private native boolean isFloatingPoint(long pointer);
-
-  /**
-   * Is this a datatype sort?
-   * @return true if the sort is a datatype sort
-   */
-  public boolean isDatatype()
-  {
-    return isDatatype(pointer);
-  }
-
-  private native boolean isDatatype(long pointer);
-
-  /**
-   * Is this a parametric datatype sort?
-   * @return true if the sort is a parametric datatype sort
-   */
-  public boolean isParametricDatatype()
-  {
-    return isParametricDatatype(pointer);
-  }
-
-  private native boolean isParametricDatatype(long pointer);
-
-  /**
-   * Is this a constructor sort?
-   * @return true if the sort is a constructor sort
-   */
-  public boolean isConstructor()
-  {
-    return isConstructor(pointer);
-  }
-
-  private native boolean isConstructor(long pointer);
-
-  /**
-   * Is this a selector sort?
-   * @return true if the sort is a selector sort
-   */
-  public boolean isSelector()
-  {
-    return isSelector(pointer);
-  }
-
-  private native boolean isSelector(long pointer);
-
-  /**
-   * Is this a tester sort?
-   * @return true if the sort is a tester sort
-   */
-  public boolean isTester()
-  {
-    return isTester(pointer);
-  }
-
-  private native boolean isTester(long pointer);
-
-  /**
-   * Is this a datatype updater sort?
-   * @return true if the sort is a datatype updater sort
-   */
-  public boolean isUpdater()
-  {
-    return isUpdater(pointer);
-  }
-
-  private native boolean isUpdater(long pointer);
-
-  /**
-   * Is this a function sort?
-   * @return true if the sort is a function sort
-   */
-  public boolean isFunction()
-  {
-    return isFunction(pointer);
-  }
-
-  private native boolean isFunction(long pointer);
-
-  /**
-   * Is this a predicate sort?
-   * That is, is this a function sort mapping to Boolean? All predicate
-   * sorts are also function sorts.
-   * @return true if the sort is a predicate sort
-   */
-  public boolean isPredicate()
-  {
-    return isPredicate(pointer);
-  }
-
-  private native boolean isPredicate(long pointer);
-
-  /**
-   * Is this a tuple sort?
-   * @return true if the sort is a tuple sort
-   */
-  public boolean isTuple()
-  {
-    return isTuple(pointer);
-  }
-
-  private native boolean isTuple(long pointer);
-
-  /**
-   * Is this a record sort?
-   * @return true if the sort is a record sort
-   */
-  public boolean isRecord()
-  {
-    return isRecord(pointer);
-  }
-
-  private native boolean isRecord(long pointer);
-
-  /**
-   * Is this an array sort?
-   * @return true if the sort is a array sort
-   */
-  public boolean isArray()
-  {
-    return isArray(pointer);
-  }
-
-  private native boolean isArray(long pointer);
-
-  /**
-   * Is this a Set sort?
-   * @return true if the sort is a Set sort
-   */
-  public boolean isSet()
-  {
-    return isSet(pointer);
-  }
-
-  private native boolean isSet(long pointer);
-
-  /**
-   * Is this a Bag sort?
-   * @return true if the sort is a Bag sort
-   */
-  public boolean isBag()
-  {
-    return isBag(pointer);
-  }
-
-  private native boolean isBag(long pointer);
-
-  /**
-   * Is this a Sequence sort?
-   * @return true if the sort is a Sequence sort
-   */
-  public boolean isSequence()
-  {
-    return isSequence(pointer);
-  }
-
-  private native boolean isSequence(long pointer);
-
-  /**
-   * Is this a sort kind?
-   * @return true if this is a sort kind
-   */
-  public boolean isUninterpretedSort()
-  {
-    return isUninterpretedSort(pointer);
-  }
-
-  private native boolean isUninterpretedSort(long pointer);
-
-  /**
-   * Is this a sort constructor kind?
-   * @return true if this is a sort constructor kind
-   */
-  public boolean isSortConstructor()
-  {
-    return isSortConstructor(pointer);
-  }
-
-  private native boolean isSortConstructor(long pointer);
-
-  /**
-   * Is this a first-class sort?
-   * First-class sorts are sorts for which:
-   * (1) we handle equalities between terms of that type, and
-   * (2) they are allowed to be parameters of parametric sorts (e.g. index or
-   *     element sorts of arrays).
-   *
-   * Examples of sorts that are not first-class include sort constructor sorts
-   * and regular expression sorts.
-   *
-   * @return true if this is a first-class sort
-   */
-  public boolean isFirstClass()
-  {
-    return isFirstClass(pointer);
-  }
-
-  private native boolean isFirstClass(long pointer);
-
-  /**
-   * Is this a function-LIKE sort?
-   *
-   * Anything function-like except arrays (e.g., datatype selectors) is
-   * considered a function here. Function-like terms can not be the argument
-   * or return value for any term that is function-like.
-   * This is mainly to avoid higher order.
-   *
-   * Note that arrays are explicitly not considered function-like here.
-   *
-   * @return true if this is a function-like sort
-   */
-  public boolean isFunctionLike()
-  {
-    return isFunctionLike(pointer);
-  }
-
-  private native boolean isFunctionLike(long pointer);
-
-  /**
-   * Is this sort a subsort of the given sort?
-   * @return true if this sort is a subsort of s
-   */
-  public boolean isSubsortOf(Sort s)
-  {
-    return isSubsortOf(pointer, s.getPointer());
-  }
-
-  private native boolean isSubsortOf(long pointer, long sortPointer);
-
-  /**
-   * Is this sort comparable to the given sort (i.e., do they share
-   * a common ancestor in the subsort tree)?
-   * @return true if this sort is comparable to s
-   */
-  public boolean isComparableTo(Sort s)
-  {
-    return isComparableTo(pointer, s.getPointer());
-  }
-
-  private native boolean isComparableTo(long pointer, long sortPointer);
-
-  /**
-   * @return the underlying datatype of a datatype sort
-   */
-  public Datatype getDatatype()
-  {
-    long datatypePointer = getDatatype(pointer);
-    return new Datatype(solver, datatypePointer);
-  }
-
-  private native long getDatatype(long pointer);
-
-  /**
-   * Instantiate a parameterized datatype/sort sort.
-   * Create sorts parameter with Solver.mkParamSort().
-   * @param params the list of sort parameters to instantiate with
-   */
-  public Sort instantiate(List<Sort> params)
-  {
-    return instantiate(params.toArray(new Sort[0]));
-  }
-
-  /**
-   * Instantiate a parameterized datatype/sort sort.
-   * Create sorts parameter with Solver.mkParamSort().
-   * @param params the list of sort parameters to instantiate with
-   */
-  public Sort instantiate(Sort[] params)
-  {
-    long[] paramsPointers = Utils.getPointers(params);
-    long sortPointer = instantiate(pointer, paramsPointers);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long instantiate(long pointer, long[] paramsPointers);
-
-  /**
-   * Substitution of Sorts.
-   * @param sort the subsort to be substituted within this sort.
-   * @param replacement the sort replacing the substituted subsort.
-   */
-  public Sort substitute(Sort sort, Sort replacement)
-  {
-    long sortPointer = substitute(pointer, sort.getPointer(), replacement.getPointer());
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long substitute(long pointer, long sortPointer, long replacementPointer);
-
-  /**
-   * Simultaneous substitution of Sorts.
-   * @param sorts the subsorts to be substituted within this sort.
-   * @param replacements the sort replacing the substituted subsorts.
-   */
-  public Sort substitute(Sort[] sorts, Sort[] replacements)
-  {
-    long[] sortPointers = Utils.getPointers(sorts);
-    long[] replacementPointers = Utils.getPointers(sorts);
-    long sortPointer = substitute(pointer, sortPointers, replacementPointers);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long substitute(long pointer, long[] sortPointers, long[] replacementPointers);
-
-  /**
-   * Output a string representation of this sort to a given stream.
-   * @param out the output stream
-   */
-  // TODO: do we need to support this?
-  // void toStream(std::ostream& out)
-
-  /**
-   * @return a string representation of this sort
-   */
-  protected native String toString(long pointer);
-
-  /* Constructor sort ------------------------------------------------------- */
-
-  /**
-   * @return the arity of a constructor sort
-   */
-  public int getConstructorArity()
-  {
-    return getConstructorArity(pointer);
-  }
-
-  private native int getConstructorArity(long pointer);
-
-  /**
-   * @return the domain sorts of a constructor sort
-   */
-  public Sort[] getConstructorDomainSorts()
-  {
-    long[] pointers = getConstructorDomainSorts(pointer);
-    return Utils.getSorts(solver, pointers);
-  }
-
-  private native long[] getConstructorDomainSorts(long pointer);
-
-  /**
-   * @return the codomain sort of a constructor sort
-   */
-  public Sort getConstructorCodomainSort()
-  {
-    long sortPointer = getConstructorCodomainSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getConstructorCodomainSort(long pointer);
-
-  /* Selector sort ------------------------------------------------------- */
-
-  /**
-   * @return the domain sort of a selector sort
-   */
-  public Sort getSelectorDomainSort()
-  {
-    long sortPointer = getSelectorDomainSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getSelectorDomainSort(long pointer);
-
-  /**
-   * @return the codomain sort of a selector sort
-   */
-  public Sort getSelectorCodomainSort()
-  {
-    long sortPointer = getSelectorCodomainSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getSelectorCodomainSort(long pointer);
-
-  /* Tester sort ------------------------------------------------------- */
-
-  /**
-   * @return the domain sort of a tester sort
-   */
-  public Sort getTesterDomainSort()
-  {
-    long sortPointer = getTesterDomainSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getTesterDomainSort(long pointer);
-
-  /**
-   * @return the codomain sort of a tester sort, which is the Boolean sort
-   */
-  public Sort getTesterCodomainSort()
-  {
-    long sortPointer = getTesterCodomainSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getTesterCodomainSort(long pointer);
-
-  /* Function sort ------------------------------------------------------- */
-
-  /**
-   * @return the arity of a function sort
-   */
-  public int getFunctionArity()
-  {
-    return getFunctionArity(pointer);
-  }
-
-  private native int getFunctionArity(long pointer);
-
-  /**
-   * @return the domain sorts of a function sort
-   */
-  public Sort[] getFunctionDomainSorts()
-  {
-    long[] pointers = getFunctionDomainSorts(pointer);
-    return Utils.getSorts(solver, pointers);
-  }
-
-  private native long[] getFunctionDomainSorts(long pointer);
-
-  /**
-   * @return the codomain sort of a function sort
-   */
-  public Sort getFunctionCodomainSort()
-  {
-    long sortPointer = getFunctionCodomainSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getFunctionCodomainSort(long pointer);
-
-  /* Array sort ---------------------------------------------------------- */
-
-  /**
-   * @return the array index sort of an array sort
-   */
-  public Sort getArrayIndexSort()
-  {
-    long sortPointer = getArrayIndexSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getArrayIndexSort(long pointer);
-
-  /**
-   * @return the array element sort of an array element sort
-   */
-  public Sort getArrayElementSort()
-  {
-    long sortPointer = getArrayElementSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getArrayElementSort(long pointer);
-
-  /* Set sort ------------------------------------------------------------ */
-
-  /**
-   * @return the element sort of a set sort
-   */
-  public Sort getSetElementSort()
-  {
-    long sortPointer = getSetElementSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getSetElementSort(long pointer);
-
-  /* Bag sort ------------------------------------------------------------ */
-
-  /**
-   * @return the element sort of a bag sort
-   */
-  public Sort getBagElementSort()
-  {
-    long sortPointer = getBagElementSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getBagElementSort(long pointer);
-
-  /* Sequence sort ------------------------------------------------------- */
-
-  /**
-   * @return the element sort of a sequence sort
-   */
-  public Sort getSequenceElementSort()
-  {
-    long sortPointer = getSequenceElementSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getSequenceElementSort(long pointer);
-
-  /* Uninterpreted sort -------------------------------------------------- */
-
-  /**
-   * @return the name of an uninterpreted sort
-   */
-  public String getUninterpretedSortName()
-  {
-    return getUninterpretedSortName(pointer);
-  }
-
-  private native String getUninterpretedSortName(long pointer);
-
-  /**
-   * @return true if an uninterpreted sort is parameterezied
-   */
-  public boolean isUninterpretedSortParameterized()
-  {
-    return isUninterpretedSortParameterized(pointer);
-  }
-
-  private native boolean isUninterpretedSortParameterized(long pointer);
-
-  /**
-   * @return the parameter sorts of an uninterpreted sort
-   */
-  public Sort[] getUninterpretedSortParamSorts()
-  {
-    long[] pointers = getUninterpretedSortParamSorts(pointer);
-    return Utils.getSorts(solver, pointers);
-  }
-
-  private native long[] getUninterpretedSortParamSorts(long pointer);
-
-  /* Sort constructor sort ----------------------------------------------- */
-
-  /**
-   * @return the name of a sort constructor sort
-   */
-  public String getSortConstructorName()
-  {
-    return getSortConstructorName(pointer);
-  }
-
-  private native String getSortConstructorName(long pointer);
-
-  /**
-   * @return the arity of a sort constructor sort
-   */
-  public int getSortConstructorArity()
-  {
-    return getSortConstructorArity(pointer);
-  }
-
-  private native int getSortConstructorArity(long pointer);
-
-  /* Bit-vector sort ----------------------------------------------------- */
-
-  /**
-   * @return the bit-width of the bit-vector sort
-   */
-  public int getBitVectorSize()
-  {
-    return getBitVectorSize(pointer);
-  }
-
-  private native int getBitVectorSize(long pointer);
-
-  /* Floating-point sort ------------------------------------------------- */
-
-  /**
-   * @return the bit-width of the exponent of the floating-point sort
-   */
-  public int getFloatingPointExponentSize()
-  {
-    return getFloatingPointExponentSize(pointer);
-  }
-
-  private native int getFloatingPointExponentSize(long pointer);
-
-  /**
-   * @return the width of the significand of the floating-point sort
-   */
-  public int getFloatingPointSignificandSize()
-  {
-    return getFloatingPointSignificandSize(pointer);
-  }
-
-  private native int getFloatingPointSignificandSize(long pointer);
-
-  /* Datatype sort ------------------------------------------------------- */
-
-  /**
-   * @return the parameter sorts of a datatype sort
-   */
-  public Sort[] getDatatypeParamSorts()
-  {
-    long[] pointers = getDatatypeParamSorts(pointer);
-    return Utils.getSorts(solver, pointers);
-  }
-
-  private native long[] getDatatypeParamSorts(long pointer);
-
-  /**
-   * @return the arity of a datatype sort
-   */
-  public int getDatatypeArity()
-  {
-    return getDatatypeArity(pointer);
-  }
-
-  private native int getDatatypeArity(long pointer);
-
-  /* Tuple sort ---------------------------------------------------------- */
-
-  /**
-   * @return the length of a tuple sort
-   */
-  public int getTupleLength()
-  {
-    return getTupleLength(pointer);
-  }
-
-  private native int getTupleLength(long pointer);
-
-  /**
-   * @return the element sorts of a tuple sort
-   */
-  public Sort[] getTupleSorts()
-  {
-    long[] pointers = getTupleSorts(pointer);
-    return Utils.getSorts(solver, pointers);
-  }
-
-  private native long[] getTupleSorts(long pointer);
-}
\ No newline at end of file
diff --git a/src/api/java/cvc5/Stat.java b/src/api/java/cvc5/Stat.java
deleted file mode 100644 (file)
index ee7d209..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.util.Map;
-
-/**
- * Represents a snapshot of a single statistic value.
- * A value can be of type {@code long}, {@code double}, {@code String} or a histogram
- * ({@code Map<String, Long>}).
- * The value type can be queried (using {@code isInt()}, {@code isDouble()}, etc.) and
- * the stored value can be accessed (using {@code getInt()}, {@code getDouble()}, etc.).
- * It is possible to query whether this statistic is an expert statistic by
- * {@code isExpert()} and whether its value is the default value by {@code isDefault()}.
- */
-public class Stat extends AbstractPointer
-{
-  // region construction and destruction
-  Stat(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * @return a string representation of this Stat
-   */
-  protected native String toString(long pointer);
-
-  /**
-   * Is this value intended for experts only?
-   * @return Whether this is an expert statistic.
-   */
-  public boolean isExpert()
-  {
-    return isExpert(pointer);
-  }
-
-  private native boolean isExpert(long pointer);
-
-  /**
-   * Does this value hold the default value?
-   * @return Whether this is a defaulted statistic.
-   */
-  public boolean isDefault()
-  {
-    return isDefault(pointer);
-  }
-
-  private native boolean isDefault(long pointer);
-
-  /**
-   * Is this value an integer?
-   * @return Whether the value is an integer.
-   */
-  public boolean isInt()
-  {
-    return isInt(pointer);
-  }
-
-  private native boolean isInt(long pointer);
-
-  /**
-   * Return the integer value.
-   * @return The integer value.
-   */
-  public long getInt()
-  {
-    return getInt(pointer);
-  }
-
-  private native long getInt(long pointer);
-
-  /**
-   * Is this value a double?
-   * @return Whether the value is a double.
-   */
-  public boolean isDouble()
-  {
-    return isDouble(pointer);
-  }
-
-  private native boolean isDouble(long pointer);
-
-  /**
-   * Return the double value.
-   * @return The double value.
-   */
-  public double getDouble()
-  {
-    return getDouble(pointer);
-  }
-
-  private native double getDouble(long pointer);
-
-  /**
-   * Is this value a string?
-   * @return Whether the value is a string.
-   */
-  public boolean isString()
-  {
-    return isString(pointer);
-  }
-
-  private native boolean isString(long pointer);
-
-  /**
-   * Return the string value.
-   * @return The string value.
-   */
-  public String getString()
-  {
-    return getString(pointer);
-  }
-
-  private native String getString(long pointer);
-
-  /**
-   * Is this value a histogram?
-   * @return Whether the value is a histogram.
-   */
-  public boolean isHistogram()
-  {
-    return isHistogram(pointer);
-  }
-
-  private native boolean isHistogram(long pointer);
-
-  /**
-   * Return the histogram value.
-   * @return The histogram value.
-   */
-  public Map<String, Long> getHistogram()
-  {
-    return getHistogram(pointer);
-  }
-
-  private native Map<String, Long> getHistogram(long pointer);
-};
diff --git a/src/api/java/cvc5/Statistics.java b/src/api/java/cvc5/Statistics.java
deleted file mode 100644 (file)
index a85220e..0000000
+++ /dev/null
@@ -1,121 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.util.Iterator;
-import java.util.NoSuchElementException;
-
-public class Statistics extends AbstractPointer implements Iterable<Pair<String, Stat>>
-{
-  // region construction and destruction
-  Statistics(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * @return a string representation of this Statistics
-   */
-  protected native String toString(long pointer);
-
-  /**
-   * Retrieve the statistic with the given name.
-   * Asserts that a statistic with the given name actually exists and throws
-   * a `CVC5ApiRecoverableException` if it does not.
-   * @param name Name of the statistic.
-   * @return The statistic with the given name.
-   */
-  public Stat get(String name)
-  {
-    long statPointer = get(pointer, name);
-    return new Stat(solver, statPointer);
-  }
-
-  private native long get(long pointer, String name);
-
-  /**
-   * Begin iteration over the statistics values.
-   * By default, only entries that are public (non-expert) and have been set
-   * are visible while the others are skipped.
-   * @param expert If set to true, expert statistics are shown as well.
-   * @param defaulted If set to true, defaulted statistics are shown as well.
-   */
-
-  private native long getIterator(long pointer);
-
-  private native boolean hasNext(long pointer, long iteratorPointer);
-
-  private native Pair<String, Long> getNext(long pointer, long iteratorPointer)
-      throws CVC5ApiException;
-
-  private native long increment(long pointer, long iteratorPointer) throws CVC5ApiException;
-
-  private native void deleteIteratorPointer(long iteratorPointer);
-
-  public class ConstIterator implements Iterator<Pair<String, Stat>>
-  {
-    private long iteratorPointer = 0;
-
-    public ConstIterator()
-    {
-      iteratorPointer = getIterator(pointer);
-    }
-
-    @Override public boolean hasNext()
-    {
-      return Statistics.this.hasNext(pointer, iteratorPointer);
-    }
-
-    @Override public Pair<String, Stat> next()
-    {
-      try
-      {
-        Pair<String, Long> pair = Statistics.this.getNext(pointer, iteratorPointer);
-        Stat stat = new Stat(solver, pair.second);
-        this.iteratorPointer = Statistics.this.increment(pointer, iteratorPointer);
-        return new Pair<>(pair.first, stat);
-      }
-      catch (CVC5ApiException e)
-      {
-        throw new NoSuchElementException(e.getMessage());
-      }
-    }
-
-    @Override public void finalize()
-    {
-      deleteIteratorPointer(iteratorPointer);
-    }
-  }
-
-  @Override public Iterator<Pair<String, Stat>> iterator()
-  {
-    return new ConstIterator();
-  }
-};
diff --git a/src/api/java/cvc5/Term.java b/src/api/java/cvc5/Term.java
deleted file mode 100644 (file)
index e2c7190..0000000
+++ /dev/null
@@ -1,688 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.math.BigInteger;
-import java.util.Arrays;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.NoSuchElementException;
-import java.util.Set;
-
-public class Term extends AbstractPointer implements Comparable<Term>, Iterable<Term>
-{
-  // region construction and destruction
-  Term(Solver solver, long pointer)
-  {
-    super(solver, pointer);
-  }
-
-  protected static native void deletePointer(long pointer);
-
-  public long getPointer()
-  {
-    return pointer;
-  }
-
-  @Override public void finalize()
-  {
-    deletePointer(pointer);
-  }
-
-  // endregion
-
-  /**
-   * Syntactic equality operator.
-   * Return true if both terms are syntactically identical.
-   * Both terms must belong to the same solver object.
-   *
-   * @param t the term to compare to for equality
-   * @return true if the terms are equal
-   */
-  @Override public boolean equals(Object t)
-  {
-    if (this == t)
-      return true;
-    if (t == null || getClass() != t.getClass())
-      return false;
-    Term term = (Term) t;
-    if (this.pointer == term.pointer)
-    {
-      return true;
-    }
-    return equals(pointer, term.getPointer());
-  }
-
-  private native boolean equals(long pointer1, long pointer2);
-
-  /**
-   * Comparison for ordering on terms.
-   *
-   * @param t the term to compare to
-   * @return a negative integer, zero, or a positive integer as this term
-   * is less than, equal to, or greater than the specified term.
-   */
-  @Override public int compareTo(Term t)
-  {
-    return this.compareTo(pointer, t.getPointer());
-  }
-
-  private native int compareTo(long pointer1, long pointer2);
-
-  /**
-   * @return the number of children of this term
-   */
-  public int getNumChildren()
-  {
-    return getNumChildren(pointer);
-  }
-
-  private native int getNumChildren(long pointer);
-
-  /**
-   * Get the child term at a given index.
-   *
-   * @param index the index of the child term to return
-   * @return the child term with the given index
-   */
-  public Term getChild(int index) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(index, "index");
-    long termPointer = getChild(pointer, index);
-    return new Term(solver, termPointer);
-  }
-
-  private native long getChild(long pointer, int index);
-
-  /**
-   * @return the id of this term
-   */
-  public long getId()
-  {
-    return getId(pointer);
-  }
-
-  private native long getId(long pointer);
-
-  /**
-   * @return the kind of this term
-   */
-  public Kind getKind() throws CVC5ApiException
-  {
-    int value = getKind(pointer);
-    return Kind.fromInt(value);
-  }
-
-  private native int getKind(long pointer);
-
-  /**
-   * @return the sort of this term
-   */
-  public Sort getSort()
-  {
-    long sortPointer = getSort(pointer);
-    return new Sort(solver, sortPointer);
-  }
-
-  private native long getSort(long pointer);
-
-  /**
-   * @return the result of replacing 'term' by 'replacement' in this term
-   */
-  public Term substitute(Term term, Term replacement)
-  {
-    long termPointer = substitute(pointer, term.getPointer(), replacement.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long substitute(long pointer, long termPointer, long replacementPointer);
-
-  /**
-   * @return the result of simultaneously replacing 'terms' by 'replacements'
-   * in this term
-   */
-  public Term substitute(List<Term> terms, List<Term> replacements)
-  {
-    return substitute(terms.toArray(new Term[0]), replacements.toArray(new Term[0]));
-  }
-
-  /**
-   * @return the result of simultaneously replacing 'terms' by 'replacements'
-   * in this term
-   */
-  public Term substitute(Term[] terms, Term[] replacements)
-  {
-    long[] termPointers = new long[terms.length];
-    for (int i = 0; i < termPointers.length; i++)
-    {
-      termPointers[i] = terms[i].getPointer();
-    }
-    long[] replacementPointers = new long[replacements.length];
-    for (int i = 0; i < replacements.length; i++)
-    {
-      replacementPointers[i] = replacements[i].getPointer();
-    }
-
-    long termPointer = substitute(pointer, termPointers, replacementPointers);
-    return new Term(solver, termPointer);
-  }
-
-  private native long substitute(long pointer, long[] termPointers, long[] replacementPointers);
-
-  /**
-   * @return true iff this term has an operator
-   */
-  public boolean hasOp()
-  {
-    return hasOp(pointer);
-  }
-
-  private native boolean hasOp(long pointer);
-
-  /**
-   * @return the Op used to create this term
-   * Note: This is safe to call when hasOp() returns true.
-   */
-  public Op getOp()
-  {
-    long opPointer = getOp(pointer);
-    return new Op(solver, opPointer);
-  }
-
-  private native long getOp(long pointer);
-
-  /**
-   * @return true if this Term is a null term
-   */
-  public boolean isNull()
-  {
-    return isNull(pointer);
-  }
-
-  private native boolean isNull(long pointer);
-
-  /**
-   * Boolean negation.
-   *
-   * @return the Boolean negation of this term
-   */
-  public Term notTerm()
-  {
-    long termPointer = notTerm(pointer);
-    return new Term(solver, termPointer);
-  }
-
-  private native long notTerm(long pointer);
-
-  /**
-   * Boolean and.
-   *
-   * @param t a Boolean term
-   * @return the conjunction of this term and the given term
-   */
-  public Term andTerm(Term t)
-  {
-    long termPointer = andTerm(pointer, t.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long andTerm(long pointer, long termPointer);
-
-  /**
-   * Boolean or.
-   *
-   * @param t a Boolean term
-   * @return the disjunction of this term and the given term
-   */
-  public Term orTerm(Term t)
-  {
-    long termPointer = orTerm(pointer, t.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long orTerm(long pointer, long termPointer);
-
-  /**
-   * Boolean exclusive or.
-   *
-   * @param t a Boolean term
-   * @return the exclusive disjunction of this term and the given term
-   */
-  public Term xorTerm(Term t)
-  {
-    long termPointer = xorTerm(pointer, t.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long xorTerm(long pointer, long termPointer);
-
-  /**
-   * Equality.
-   *
-   * @param t a Boolean term
-   * @return the Boolean equivalence of this term and the given term
-   */
-  public Term eqTerm(Term t)
-  {
-    long termPointer = eqTerm(pointer, t.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long eqTerm(long pointer, long termPointer);
-
-  /**
-   * Boolean implication.
-   *
-   * @param t a Boolean term
-   * @return the implication of this term and the given term
-   */
-  public Term impTerm(Term t)
-  {
-    long termPointer = impTerm(pointer, t.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long impTerm(long pointer, long termPointer);
-
-  /**
-   * If-then-else with this term as the Boolean condition.
-   *
-   * @param thenTerm the 'then' term
-   * @param elseTerm the 'else' term
-   * @return the if-then-else term with this term as the Boolean condition
-   */
-  public Term iteTerm(Term thenTerm, Term elseTerm)
-  {
-    long termPointer = iteTerm(pointer, thenTerm.getPointer(), elseTerm.getPointer());
-    return new Term(solver, termPointer);
-  }
-
-  private native long iteTerm(long pointer, long thenPointer, long elsePointer);
-
-  /**
-   * @return a string representation of this term.
-   */
-  protected native String toString(long pointer);
-
-  /**
-   * @return true if the term is an integer value.
-   */
-  public boolean isIntegerValue()
-  {
-    return isIntegerValue(pointer);
-  }
-
-  private native boolean isIntegerValue(long pointer);
-
-  /**
-   * Asserts isIntegerValue().
-   * @return the integer represented by this term.
-   */
-  public BigInteger getIntegerValue()
-  {
-    return new BigInteger(getIntegerValue(pointer));
-  }
-
-  private native String getIntegerValue(long pointer);
-
-  /**
-   * @return true if the term is a string constant.
-   */
-  public boolean isStringValue()
-  {
-    return isStringValue(pointer);
-  }
-
-  private native boolean isStringValue(long pointer);
-
-  /**
-   * @return the stored string constant.
-   * <p>
-   * Note: This method is not to be confused with toString() which returns the
-   * term in some string representation, whatever data it may hold.
-   * Asserts isString().
-   */
-  public String getStringValue()
-  {
-    return getStringValue(pointer);
-  }
-
-  private native String getStringValue(long pointer);
-
-  /**
-   * @return true if the term is a rational value.
-   */
-  public boolean isRealValue()
-  {
-    return isRealValue(pointer);
-  }
-
-  private native boolean isRealValue(long pointer);
-
-  /**
-   * Asserts isRealValue().
-   * @return the representation of a rational value as a pair of its numerator
-   * and denominator.
-   */
-  public Pair<BigInteger, BigInteger> getRealValue()
-  {
-    String rational = getRealValue(pointer);
-    return Utils.getRational(rational);
-  }
-
-  private native String getRealValue(long pointer);
-
-  /**
-   * @return true if the term is a constant array.
-   */
-  public boolean isConstArray()
-  {
-    return isConstArray(pointer);
-  }
-
-  private native boolean isConstArray(long pointer);
-
-  /**
-   * Asserts isConstArray().
-   * @return the base (element stored at all indices) of a constant array
-   */
-  public Term getConstArrayBase()
-  {
-    long termPointer = getConstArrayBase(pointer);
-    return new Term(solver, termPointer);
-  }
-
-  private native long getConstArrayBase(long pointer);
-
-  /**
-   * @return true if the term is a Boolean value.
-   */
-  public boolean isBooleanValue()
-  {
-    return isBooleanValue(pointer);
-  }
-
-  private native boolean isBooleanValue(long pointer);
-  /**
-   * Asserts isBooleanValue().
-   * @return the representation of a Boolean value as a native Boolean value.
-   */
-  public boolean getBooleanValue()
-  {
-    return getBooleanValue(pointer);
-  }
-
-  private native boolean getBooleanValue(long pointer);
-
-  /**
-   * @return true if the term is a bit-vector value.
-   */
-  public boolean isBitVectorValue()
-  {
-    return isBitVectorValue(pointer);
-  }
-
-  private native boolean isBitVectorValue(long pointer);
-
-  /**
-   * Asserts isBitVectorValue().
-   * @return the representation of a bit-vector value in bit string representation.
-   */
-  public String getBitVectorValue() throws CVC5ApiException
-  {
-    return getBitVectorValue(2);
-  }
-
-  /**
-   * Asserts isBitVectorValue().
-   * @return the representation of a bit-vector value in string representation.
-   * Supported bases are 2 (bit string), 10 (decimal string) or 16 (hexadecimal
-   * string).
-   */
-  public String getBitVectorValue(int base) throws CVC5ApiException
-  {
-    Utils.validateUnsigned(base, "base");
-    return getBitVectorValue(pointer, base);
-  }
-
-  private native String getBitVectorValue(long pointer, int base);
-
-  /**
-   * @return true if the term is an abstract value.
-   */
-  public boolean isAbstractValue()
-  {
-    return isAbstractValue(pointer);
-  }
-
-  private native boolean isAbstractValue(long pointer);
-
-  /**
-   * Asserts isAbstractValue().
-   * @return the representation of an abstract value as a string.
-   */
-  public String getAbstractValue()
-  {
-    return getAbstractValue(pointer);
-  }
-
-  private native String getAbstractValue(long pointer);
-
-  /**
-   * @return true if the term is a tuple value.
-   */
-  public boolean isTupleValue()
-  {
-    return isTupleValue(pointer);
-  }
-
-  private native boolean isTupleValue(long pointer);
-
-  /**
-   * Asserts isTupleValue().
-   * @return the representation of a tuple value as a vector of terms.
-   */
-  public Term[] getTupleValue()
-  {
-    long[] termPointers = getTupleValue(pointer);
-    return Utils.getTerms(solver, termPointers);
-  }
-
-  private native long[] getTupleValue(long pointer);
-
-  /**
-   * @return true if the term is the floating-point value for positive zero.
-   */
-  public boolean isFloatingPointPosZero()
-  {
-    return isFloatingPointPosZero(pointer);
-  }
-
-  private native boolean isFloatingPointPosZero(long pointer);
-  /**
-   * @return true if the term is the floating-point value for negative zero.
-   */
-  public boolean isFloatingPointNegZero()
-  {
-    return isFloatingPointNegZero(pointer);
-  }
-
-  private native boolean isFloatingPointNegZero(long pointer);
-  /**
-   * @return true if the term is the floating-point value for positive
-   * infinity.
-   */
-  public boolean isFloatingPointPosInf()
-  {
-    return isFloatingPointPosInf(pointer);
-  }
-
-  private native boolean isFloatingPointPosInf(long pointer);
-  /**
-   * @return true if the term is the floating-point value for negative
-   * infinity.
-   */
-  public boolean isFloatingPointNegInf()
-  {
-    return isFloatingPointNegInf(pointer);
-  }
-
-  private native boolean isFloatingPointNegInf(long pointer);
-  /**
-   * @return true if the term is the floating-point value for not a number.
-   */
-  public boolean isFloatingPointNaN()
-  {
-    return isFloatingPointNaN(pointer);
-  }
-
-  private native boolean isFloatingPointNaN(long pointer);
-  /**
-   * @return true if the term is a floating-point value.
-   */
-  public boolean isFloatingPointValue()
-  {
-    return isFloatingPointValue(pointer);
-  }
-
-  private native boolean isFloatingPointValue(long pointer);
-  /**
-   * Asserts isFloatingPointValue().
-   * @return the representation of a floating-point value as a tuple of the
-   * exponent width, the significand width and a bit-vector value.
-   */
-  public Triplet<Long, Long, Term> getFloatingPointValue()
-  {
-    Triplet<Long, Long, Long> triplet = getFloatingPointValue(pointer);
-    return new Triplet(triplet.first, triplet.second, new Term(solver, triplet.third));
-  }
-
-  private native Triplet<Long, Long, Long> getFloatingPointValue(long pointer);
-
-  /**
-   * @return true if the term is a set value.
-   */
-  public boolean isSetValue()
-  {
-    return isSetValue(pointer);
-  }
-
-  private native boolean isSetValue(long pointer);
-  /**
-   * Asserts isSetValue().
-   * @return the representation of a set value as a set of terms.
-   */
-  public Set<Term> getSetValue()
-  {
-    long[] termPointers = getSetValue(pointer);
-    Term[] terms = Utils.getTerms(solver, termPointers);
-    return new HashSet<Term>(Arrays.asList(terms));
-  }
-
-  private native long[] getSetValue(long pointer);
-
-  /**
-   * @return true if the term is a sequence value.
-   */
-  public boolean isSequenceValue()
-  {
-    return isSequenceValue(pointer);
-  }
-
-  private native boolean isSequenceValue(long pointer);
-
-  /**
-   * Asserts isSequenceValue().
-   * Note that it is usually necessary for sequences to call
-   * `Solver::simplify()` to turn a sequence that is constructed by, e.g.,
-   * concatenation of unit sequences, into a sequence value.
-   * @return the representation of a sequence value as a vector of terms.
-   */
-  public Term[] getSequenceValue()
-  {
-    long[] termPointers = getSequenceValue(pointer);
-    return Utils.getTerms(solver, termPointers);
-  }
-
-  private native long[] getSequenceValue(long pointer);
-
-  /**
-   * @return true if the term is a value from an uninterpreted sort.
-   */
-  public boolean isUninterpretedValue()
-  {
-    return isUninterpretedValue(pointer);
-  }
-
-  private native boolean isUninterpretedValue(long pointer);
-
-  /**
-  boolean @return()
-   * Asserts isUninterpretedValue().
-   * @return the representation of an uninterpreted value as a pair of its
-  sort and its
-   * index.
-   */
-  public Pair<Sort, Integer> getUninterpretedValue()
-  {
-    Pair<Long, Integer> pair = getUninterpretedValue(pointer);
-    Sort sort = new Sort(solver, pair.first);
-    return new Pair<Sort, Integer>(sort, pair.second);
-  }
-
-  private native Pair<Long, Integer> getUninterpretedValue(long pointer);
-
-  public class ConstIterator implements Iterator<Term>
-  {
-    private int currentIndex;
-    private int size;
-
-    public ConstIterator()
-    {
-      currentIndex = -1;
-      size = getNumChildren();
-    }
-
-    @Override public boolean hasNext()
-    {
-      return currentIndex < size - 1;
-    }
-
-    @Override public Term next()
-    {
-      if (currentIndex >= size - 1)
-      {
-        throw new NoSuchElementException();
-      }
-      currentIndex++;
-      try
-      {
-        return getChild(currentIndex);
-      }
-      catch (CVC5ApiException e)
-      {
-        e.printStackTrace();
-        throw new RuntimeException(e.getMessage());
-      }
-    }
-  }
-
-  @Override public Iterator<Term> iterator()
-  {
-    return new ConstIterator();
-  }
-}
diff --git a/src/api/java/cvc5/Triplet.java b/src/api/java/cvc5/Triplet.java
deleted file mode 100644 (file)
index 0ba75e7..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-public class Triplet<A, B, C>
-{
-  public A first;
-  public B second;
-  public C third;
-  public Triplet(A first, B second, C third)
-  {
-    this.first = first;
-    this.second = second;
-    this.third = third;
-  }
-
-  @Override public boolean equals(Object object)
-  {
-    if (this == object)
-      return true;
-    if (object == null || getClass() != object.getClass())
-      return false;
-
-    Triplet<A, B, C> triplet = (Triplet<A, B, C>) object;
-    return this.first.equals(triplet.first) && this.second.equals(triplet.second)
-        && this.third.equals(triplet.third);
-  }
-}
diff --git a/src/api/java/cvc5/Utils.java b/src/api/java/cvc5/Utils.java
deleted file mode 100644 (file)
index ce8632c..0000000
+++ /dev/null
@@ -1,221 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 java API.
- */
-
-package cvc5;
-
-import java.io.IOException;
-import java.math.BigInteger;
-import java.util.ArrayList;
-import java.util.List;
-
-public class Utils
-{
-  static
-  {
-    loadLibraries();
-  }
-
-  /**
-   * load cvc5 jni library
-   */
-  public static void loadLibraries()
-  {
-    System.loadLibrary("cvc5jni");
-  }
-
-  /**
-   * return sorts array from array of pointers
-   */
-  public static Sort[] getSorts(Solver solver, long[] pointers)
-  {
-    Sort[] sorts = new Sort[pointers.length];
-    for (int i = 0; i < pointers.length; i++)
-    {
-      sorts[i] = new Sort(solver, pointers[i]);
-    }
-    return sorts;
-  }
-
-  /**
-   * return terms array from array of pointers
-   */
-  public static Term[] getTerms(Solver solver, long[] pointers)
-  {
-    Term[] terms = new Term[pointers.length];
-    for (int i = 0; i < pointers.length; i++)
-    {
-      terms[i] = new Term(solver, pointers[i]);
-    }
-    return terms;
-  }
-
-  /**
-   * get pointers from one dimensional array
-   */
-  public static long[] getPointers(IPointer[] objects)
-  {
-    long[] pointers = new long[objects.length];
-    for (int i = 0; i < pointers.length; i++)
-    {
-      pointers[i] = objects[i].getPointer();
-    }
-    return pointers;
-  }
-
-  /**
-   * get pointers from two dimensional matrix
-   */
-  public static long[][] getPointers(IPointer[][] objects)
-  {
-    long[][] pointers = new long[objects.length][];
-    for (int i = 0; i < pointers.length; i++)
-    {
-      pointers[i] = new long[objects[i].length];
-      for (int j = 0; j < objects[i].length; j++)
-      {
-        pointers[i][j] = objects[i][j].getPointer();
-      }
-    }
-    return pointers;
-  }
-
-  public static void validateUnsigned(int integer, String name) throws CVC5ApiException
-  {
-    if (integer < 0)
-    {
-      throw new CVC5ApiException("Expected " + name + " '" + integer + "' to be non negative.");
-    }
-  }
-
-  public static void validateUnsigned(long integer, String name) throws CVC5ApiException
-  {
-    if (integer < 0)
-    {
-      throw new CVC5ApiException("Expected " + name + " '" + integer + "' to be non negative.");
-    }
-  }
-
-  public static void validateUnsigned(int[] integers, String name) throws CVC5ApiException
-  {
-    for (int i = 0; i < integers.length; i++)
-    {
-      if (integers[i] < 0)
-      {
-        throw new CVC5ApiException(
-            "Expected " + name + "[" + i + "] '" + integers[i] + "' to be non negative.");
-      }
-    }
-  }
-
-  public static void validateUnsigned(long[] integers, String name) throws CVC5ApiException
-  {
-    for (int i = 0; i < integers.length; i++)
-    {
-      if (integers[i] < 0)
-      {
-        throw new CVC5ApiException(
-            "Expected " + name + "[" + i + "] '" + integers[i] + "' to be non negative.");
-      }
-    }
-  }
-
-  public static <K> Pair<K, Long>[] getPairs(Pair<K, ? extends AbstractPointer>[] abstractPointers)
-  {
-    Pair<K, Long>[] pointers = new Pair[abstractPointers.length];
-    for (int i = 0; i < pointers.length; i++)
-    {
-      pointers[i] = new Pair<>(abstractPointers[i].first, abstractPointers[i].second.getPointer());
-    }
-    return pointers;
-  }
-
-  /**
-    Convert a rational string a/b to a pair of BigIntegers
-  */
-  public static Pair<BigInteger, BigInteger> getRational(String rational)
-  {
-    if (rational.contains("/"))
-    {
-      String[] pair = rational.split("/");
-      return new Pair<>(new BigInteger(pair[0]), new BigInteger(pair[1]));
-    }
-    return new Pair<>(new BigInteger(rational), new BigInteger("1"));
-  }
-
-  /**
-     Convert a pair of BigIntegers to a rational string a/b
-   */
-  public static String getRational(Pair<BigInteger, BigInteger> pair)
-  {
-    return pair.first.toString() + "/" + pair.second.toString();
-  }
-
-  /**
-   * Get the string version of define-fun command.
-   * @param f the function to print
-   * @param params the function parameters
-   * @param body the function body
-   * @return a string version of define-fun
-   */
-  private static String defineFunToString(Term f, Term[] params, Term body)
-  {
-    Sort sort = f.getSort();
-    if (sort.isFunction())
-    {
-      sort = sort.getFunctionCodomainSort();
-    }
-    StringBuilder ss = new StringBuilder();
-    ss.append("(define-fun ").append(f).append(" (");
-    for (int i = 0; i < params.length; ++i)
-    {
-      if (i > 0)
-      {
-        ss.append(' ');
-      }
-      ss.append('(').append(params[i]).append(' ').append(params[i].getSort()).append(')');
-    }
-    ss.append(") ").append(sort).append(' ').append(body).append(')');
-    return ss.toString();
-  }
-
-  /**
-   * Print solutions for synthesis conjecture to the standard output stream.
-   * @param terms the terms for which the synthesis solutions were retrieved
-   * @param sols the synthesis solutions of the given terms
-   */
-  public static void printSynthSolutions(Term[] terms, Term[] sols) throws CVC5ApiException
-  {
-    System.out.println('(');
-
-    for (int i = 0; i < terms.length; ++i)
-    {
-      List<Term> params = new ArrayList<>();
-      Term body = null;
-      if (sols[i].getKind() == Kind.LAMBDA)
-      {
-        for (Term t : sols[i].getChild(0))
-        {
-          params.add(t);
-        }
-        body = sols[i].getChild(1);
-      }
-      if (body != null)
-      {
-        System.out.println("  " + defineFunToString(terms[i], params.toArray(new Term[0]), body));
-      }
-    }
-    System.out.println(')');
-  }
-}
index 15de21805620ef89224efca17c5a4b23e9f9722b..a15472a1a4e1cdf957b694844f4ed41d4ae71878 100644 (file)
@@ -35,7 +35,7 @@ DEFAULT_PREFIX = 'Kind'
 # Code Blocks
 
 KINDS_JAVA_TOP = \
-    r"""package cvc5;
+    r"""package io.github.cvc5.api;
 
 import java.util.HashMap;
 import java.util.Map;
diff --git a/src/api/java/io/github/cvc5/api/AbstractPointer.java b/src/api/java/io/github/cvc5/api/AbstractPointer.java
new file mode 100644 (file)
index 0000000..092e33d
--- /dev/null
@@ -0,0 +1,45 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+abstract class AbstractPointer implements IPointer
+{
+  protected final Solver solver;
+  protected final long pointer;
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  public Solver getSolver()
+  {
+    return solver;
+  }
+
+  @Override public String toString()
+  {
+    return toString(pointer);
+  }
+
+  abstract protected String toString(long pointer);
+
+  AbstractPointer(Solver solver, long pointer)
+  {
+    this.solver = solver;
+    this.pointer = pointer;
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/CVC5ApiException.java b/src/api/java/io/github/cvc5/api/CVC5ApiException.java
new file mode 100644 (file)
index 0000000..dd5766e
--- /dev/null
@@ -0,0 +1,24 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class CVC5ApiException extends Exception
+{
+  public CVC5ApiException(String message)
+  {
+    super(message);
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/CVC5ApiOptionException.java b/src/api/java/io/github/cvc5/api/CVC5ApiOptionException.java
new file mode 100644 (file)
index 0000000..0c213a7
--- /dev/null
@@ -0,0 +1,24 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Gereon Kremer, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class CVC5ApiOptionException extends CVC5ApiRecoverableException
+{
+  public CVC5ApiOptionException(String message)
+  {
+    super(message);
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/CVC5ApiRecoverableException.java b/src/api/java/io/github/cvc5/api/CVC5ApiRecoverableException.java
new file mode 100644 (file)
index 0000000..302b02e
--- /dev/null
@@ -0,0 +1,24 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class CVC5ApiRecoverableException extends CVC5ApiException
+{
+  public CVC5ApiRecoverableException(String message)
+  {
+    super(message);
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/Datatype.java b/src/api/java/io/github/cvc5/api/Datatype.java
new file mode 100644 (file)
index 0000000..c5422c2
--- /dev/null
@@ -0,0 +1,233 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.util.Iterator;
+import java.util.NoSuchElementException;
+
+public class Datatype extends AbstractPointer implements Iterable<DatatypeConstructor>
+{
+  // region construction and destruction
+  Datatype(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * Get the datatype constructor at a given index.
+   * @param idx the index of the datatype constructor to return
+   * @return the datatype constructor with the given index
+   */
+  public DatatypeConstructor getConstructor(int idx)
+  {
+    long constructorPointer = getConstructor(pointer, idx);
+    return new DatatypeConstructor(solver, constructorPointer);
+  }
+
+  private native long getConstructor(long pointer, int index);
+
+  /**
+   * Get the datatype constructor with the given name.
+   * This is a linear search through the constructors, so in case of multiple,
+   * similarly-named constructors, the first is returned.
+   * @param name the name of the datatype constructor
+   * @return the datatype constructor with the given name
+   */
+  public DatatypeConstructor getConstructor(String name)
+  {
+    long constructorPointer = getConstructor(pointer, name);
+    return new DatatypeConstructor(solver, constructorPointer);
+  }
+
+  private native long getConstructor(long pointer, String name);
+
+  /**
+   * Get a term representing the datatype constructor with the given name.
+   * This is a linear search through the constructors, so in case of multiple,
+   * similarly-named constructors, the
+   * first is returned.
+   */
+  public Term getConstructorTerm(String name)
+  {
+    long termPointer = getConstructorTerm(pointer, name);
+    return new Term(solver, termPointer);
+  }
+
+  private native long getConstructorTerm(long pointer, String name);
+
+  /**
+   * Get the datatype constructor with the given name.
+   * This is a linear search through the constructors and their selectors, so
+   * in case of multiple, similarly-named selectors, the first is returned.
+   * @param name the name of the datatype selector
+   * @return the datatype selector with the given name
+   */
+  public DatatypeSelector getSelector(String name)
+  {
+    long selectorPointer = getSelector(pointer, name);
+    return new DatatypeSelector(solver, selectorPointer);
+  }
+
+  private native long getSelector(long pointer, String name);
+
+  /** @return the name of this Datatype. */
+  public String getName()
+  {
+    return getName(pointer);
+  }
+
+  private native String getName(long pointer);
+
+  /** @return the number of constructors for this Datatype. */
+  public int getNumConstructors()
+  {
+    return getNumConstructors(pointer);
+  }
+
+  private native int getNumConstructors(long pointer);
+
+  /** @return true if this datatype is parametric */
+  public boolean isParametric()
+  {
+    return isParametric(pointer);
+  }
+
+  private native boolean isParametric(long pointer);
+
+  /** @return true if this datatype corresponds to a co-datatype */
+  public boolean isCodatatype()
+  {
+    return isCodatatype(pointer);
+  }
+
+  private native boolean isCodatatype(long pointer);
+
+  /** @return true if this datatype corresponds to a tuple */
+  public boolean isTuple()
+  {
+    return isTuple(pointer);
+  }
+
+  private native boolean isTuple(long pointer);
+
+  /** @return true if this datatype corresponds to a record */
+  public boolean isRecord()
+  {
+    return isRecord(pointer);
+  }
+
+  private native boolean isRecord(long pointer);
+
+  /** @return true if this datatype is finite */
+  public boolean isFinite()
+  {
+    return isFinite(pointer);
+  }
+
+  private native boolean isFinite(long pointer);
+
+  /**
+   * Is this datatype well-founded? If this datatype is not a codatatype,
+   * this returns false if there are no values of this datatype that are of
+   * finite size.
+   *
+   * @return true if this datatype is well-founded
+   */
+  public boolean isWellFounded()
+  {
+    return isWellFounded(pointer);
+  }
+
+  private native boolean isWellFounded(long pointer);
+
+  /**
+   * Does this datatype have nested recursion? This method returns false if a
+   * value of this datatype includes a subterm of its type that is nested
+   * beneath a non-datatype type constructor. For example, a datatype
+   * T containing a constructor having a selector with range type (Set T) has
+   * nested recursion.
+   *
+   * @return true if this datatype has nested recursion
+   */
+  public boolean hasNestedRecursion()
+  {
+    return hasNestedRecursion(pointer);
+  }
+
+  private native boolean hasNestedRecursion(long pointer);
+
+  /**
+   * @return true if this Datatype is a null object
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * @return a string representation of this datatype
+   */
+  protected native String toString(long pointer);
+
+  public class ConstIterator implements Iterator<DatatypeConstructor>
+  {
+    private int currentIndex;
+    private int size;
+
+    public ConstIterator()
+    {
+      currentIndex = -1;
+      size = getNumConstructors();
+    }
+
+    @Override public boolean hasNext()
+    {
+      return currentIndex < size - 1;
+    }
+
+    @Override public DatatypeConstructor next()
+    {
+      if (currentIndex >= size - 1)
+      {
+        throw new NoSuchElementException();
+      }
+      currentIndex++;
+
+      return getConstructor(currentIndex);
+    }
+  }
+
+  @Override public Iterator<DatatypeConstructor> iterator()
+  {
+    return new ConstIterator();
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/DatatypeConstructor.java b/src/api/java/io/github/cvc5/api/DatatypeConstructor.java
new file mode 100644 (file)
index 0000000..f41acee
--- /dev/null
@@ -0,0 +1,197 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.util.Iterator;
+import java.util.NoSuchElementException;
+
+public class DatatypeConstructor extends AbstractPointer implements Iterable<DatatypeSelector>
+{
+  // region construction and destruction
+  DatatypeConstructor(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /** @return the name of this Datatype constructor. */
+  public String getName()
+  {
+    return getName(pointer);
+  }
+
+  private native String getName(long pointer);
+
+  /**
+   * Get the constructor operator of this datatype constructor.
+   * @return the constructor term
+   */
+  public Term getConstructorTerm()
+  {
+    long termPointer = getConstructorTerm(pointer);
+    return new Term(solver, termPointer);
+  }
+
+  private native long getConstructorTerm(long pointer);
+
+  /**
+   * Get the constructor operator of this datatype constructor whose return
+   * type is retSort. This method is intended to be used on constructors of
+   * parametric datatypes and can be seen as returning the constructor
+   * term that has been explicitly cast to the given sort.
+   *
+   * This method is required for constructors of parametric datatypes whose
+   * return type cannot be determined by type inference. For example, given:
+   *   (declare-datatype List (par (T) ((nil) (cons (head T) (tail (List T))))))
+   * The type of nil terms need to be provided by the user. In SMT version 2.6,
+   * this is done via the syntax for qualified identifiers:
+   *   (as nil (List Int))
+   * This method is equivalent of applying the above, where this
+   * DatatypeConstructor is the one corresponding to nil, and retSort is
+   * (List Int).
+   *
+   * Furthermore note that the returned constructor term t is an operator,
+   * while Solver::mkTerm(APPLY_CONSTRUCTOR, t) is used to construct the above
+   * (nullary) application of nil.
+   *
+   * @param retSort the desired return sort of the constructor
+   * @return the constructor term
+   */
+  public Term getSpecializedConstructorTerm(Sort retSort)
+  {
+    long termPointer = getSpecializedConstructorTerm(pointer, retSort.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long getSpecializedConstructorTerm(long pointer, long retSortPointer);
+
+  /**
+   * Get the tester operator of this datatype constructor.
+   * @return the tester operator
+   */
+  public Term getTesterTerm()
+  {
+    long termPointer = getTesterTerm(pointer);
+    return new Term(solver, termPointer);
+  }
+  private native long getTesterTerm(long pointer);
+
+  /**
+   * @return the number of selectors (so far) of this Datatype constructor.
+   */
+  public int getNumSelectors()
+  {
+    return getNumSelectors(pointer);
+  }
+  private native int getNumSelectors(long pointer);
+
+  /** @return the i^th DatatypeSelector. */
+  public DatatypeSelector getSelector(int index)
+  {
+    long selectorPointer = getSelector(pointer, index);
+    return new DatatypeSelector(solver, selectorPointer);
+  }
+  private native long getSelector(long pointer, int index);
+
+  /**
+   * Get the datatype selector with the given name.
+   * This is a linear search through the selectors, so in case of
+   * multiple, similarly-named selectors, the first is returned.
+   * @param name the name of the datatype selector
+   * @return the first datatype selector with the given name
+   */
+  public DatatypeSelector getSelector(String name)
+  {
+    long selectorPointer = getSelector(pointer, name);
+    return new DatatypeSelector(solver, selectorPointer);
+  }
+  private native long getSelector(long pointer, String name);
+
+  /**
+   * Get the term representation of the datatype selector with the given name.
+   * This is a linear search through the arguments, so in case of multiple,
+   * similarly-named arguments, the selector for the first is returned.
+   * @param name the name of the datatype selector
+   * @return a term representing the datatype selector with the given name
+   */
+  public Term getSelectorTerm(String name)
+  {
+    long termPointer = getSelectorTerm(pointer, name);
+    return new Term(solver, termPointer);
+  }
+  private native long getSelectorTerm(long pointer, String name);
+
+  /**
+   * @return true if this DatatypeConstructor is a null object
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * @return a string representation of this datatype constructor
+   */
+  protected native String toString(long pointer);
+
+  public class ConstIterator implements Iterator<DatatypeSelector>
+  {
+    private int currentIndex;
+    private int size;
+
+    public ConstIterator()
+    {
+      currentIndex = -1;
+      size = getNumSelectors();
+    }
+
+    @Override public boolean hasNext()
+    {
+      return currentIndex < size - 1;
+    }
+
+    @Override public DatatypeSelector next()
+    {
+      if (currentIndex >= size - 1)
+      {
+        throw new NoSuchElementException();
+      }
+      currentIndex++;
+
+      return getSelector(currentIndex);
+    }
+  }
+
+  @Override public Iterator<DatatypeSelector> iterator()
+  {
+    return new ConstIterator();
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/DatatypeConstructorDecl.java b/src/api/java/io/github/cvc5/api/DatatypeConstructorDecl.java
new file mode 100644 (file)
index 0000000..da3fa35
--- /dev/null
@@ -0,0 +1,77 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class DatatypeConstructorDecl extends AbstractPointer
+{
+  // region construction and destruction
+  DatatypeConstructorDecl(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * Add datatype selector declaration.
+   * @param name the name of the datatype selector declaration to add
+   * @param sort the range sort of the datatype selector declaration to add
+   */
+  public void addSelector(String name, Sort sort)
+  {
+    addSelector(pointer, name, sort.getPointer());
+  }
+
+  private native void addSelector(long pointer, String name, long sortPointer);
+
+  /**
+   * Add datatype selector declaration whose range type is the datatype itself.
+   * @param name the name of the datatype selector declaration to add
+   */
+  public void addSelectorSelf(String name)
+  {
+    addSelectorSelf(pointer, name);
+  }
+
+  private native void addSelectorSelf(long pointer, String name);
+
+  /**
+   * @return true if this DatatypeConstructorDecl is a null declaration.
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * @return a string representation of this datatype constructor declaration
+   */
+  protected native String toString(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/DatatypeDecl.java b/src/api/java/io/github/cvc5/api/DatatypeDecl.java
new file mode 100644 (file)
index 0000000..ad90c09
--- /dev/null
@@ -0,0 +1,88 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class DatatypeDecl extends AbstractPointer
+{
+  // region construction and destruction
+  DatatypeDecl(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+  /**
+   * Add datatype constructor declaration.
+   * @param ctor the datatype constructor declaration to add
+   */
+  public void addConstructor(DatatypeConstructorDecl ctor)
+  {
+    addConstructor(pointer, ctor.getPointer());
+  }
+
+  private native void addConstructor(long pointer, long declPointer);
+
+  /** Get the number of constructors (so far) for this Datatype declaration. */
+  int getNumConstructors()
+  {
+    return getNumConstructors(pointer);
+  }
+
+  private native int getNumConstructors(long pointer);
+
+  /** Is this Datatype declaration parametric? */
+  public boolean isParametric()
+  {
+    return isParametric(pointer);
+  }
+
+  private native boolean isParametric(long pointer);
+
+  /**
+   * @return true if this DatatypeDecl is a null object
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * @return a string representation of this datatype declaration
+   */
+  protected native String toString(long pointer);
+
+  /** @return the name of this datatype declaration. */
+  public String getName()
+  {
+    return getName(pointer);
+  }
+
+  private native String getName(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/DatatypeSelector.java b/src/api/java/io/github/cvc5/api/DatatypeSelector.java
new file mode 100644 (file)
index 0000000..7a0907c
--- /dev/null
@@ -0,0 +1,95 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class DatatypeSelector extends AbstractPointer
+{
+  // region construction and destruction
+  DatatypeSelector(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /** @return the name of this Datatype selector. */
+  public String getName()
+  {
+    return getName(pointer);
+  }
+
+  private native String getName(long pointer);
+
+  /**
+   * Get the selector operator of this datatype selector.
+   * @return the selector term
+   */
+  public Term getSelectorTerm()
+  {
+    long termPointer = getSelectorTerm(pointer);
+    return new Term(solver, termPointer);
+  }
+
+  private native long getSelectorTerm(long pointer);
+
+  /**
+   * Get the upater operator of this datatype selector.
+   * @return the updater term
+   */
+  public Term getUpdaterTerm()
+  {
+    long termPointer = getUpdaterTerm(pointer);
+    return new Term(solver, termPointer);
+  }
+
+  private native long getUpdaterTerm(long pointer);
+
+  /** @return the range sort of this selector. */
+  public Sort getRangeSort()
+  {
+    long sortPointer = getRangeSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getRangeSort(long pointer);
+
+  /**
+   * @return true if this DatatypeSelector is a null object
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * @return a string representation of this datatype selector
+   */
+  protected native String toString(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/Grammar.java b/src/api/java/io/github/cvc5/api/Grammar.java
new file mode 100644 (file)
index 0000000..860bb83
--- /dev/null
@@ -0,0 +1,99 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class Grammar extends AbstractPointer
+{
+  // region construction and destruction
+  Grammar(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  public Grammar(Grammar grammar)
+  {
+    super(grammar.solver, copyGrammar(grammar.pointer));
+  }
+
+  private static native long copyGrammar(long pointer);
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * Add \p rule to the set of rules corresponding to \p ntSymbol.
+   * @param ntSymbol the non-terminal to which the rule is added
+   * @param rule the rule to add
+   */
+  public void addRule(Term ntSymbol, Term rule)
+  {
+    addRule(pointer, ntSymbol.getPointer(), rule.getPointer());
+  }
+
+  private native void addRule(long pointer, long ntSymbolPointer, long rulePointer);
+
+  /**
+   * Add \p rules to the set of rules corresponding to \p ntSymbol.
+   * @param ntSymbol the non-terminal to which the rules are added
+   * @param rules the rules to add
+   */
+  public void addRules(Term ntSymbol, Term[] rules)
+  {
+    long[] pointers = Utils.getPointers(rules);
+    addRules(pointer, ntSymbol.getPointer(), pointers);
+  }
+
+  public native void addRules(long pointer, long ntSymbolPointer, long[] rulePointers);
+
+  /**
+   * Allow \p ntSymbol to be an arbitrary constant.
+   * @param ntSymbol the non-terminal allowed to be any constant
+   */
+  public void addAnyConstant(Term ntSymbol)
+  {
+    addAnyConstant(pointer, ntSymbol.getPointer());
+  }
+
+  private native void addAnyConstant(long pointer, long ntSymbolPointer);
+
+  /**
+   * Allow \p ntSymbol to be any input variable to corresponding
+   * synth-fun/synth-inv with the same sort as \p ntSymbol.
+   * @param ntSymbol the non-terminal allowed to be any input constant
+   */
+  public void addAnyVariable(Term ntSymbol)
+  {
+    addAnyVariable(pointer, ntSymbol.getPointer());
+  }
+
+  private native void addAnyVariable(long pointer, long ntSymbolPointer);
+
+  /**
+   * @return a string representation of this grammar.
+   */
+  protected native String toString(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/IPointer.java b/src/api/java/io/github/cvc5/api/IPointer.java
new file mode 100644 (file)
index 0000000..383ef51
--- /dev/null
@@ -0,0 +1,21 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+interface IPointer
+{
+  long getPointer();
+}
diff --git a/src/api/java/io/github/cvc5/api/Op.java b/src/api/java/io/github/cvc5/api/Op.java
new file mode 100644 (file)
index 0000000..86d8937
--- /dev/null
@@ -0,0 +1,137 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class Op extends AbstractPointer
+{
+  // region construction and destruction
+  Op(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * Syntactic equality operator.
+   * Return true if both operators are syntactically identical.
+   * Both operators must belong to the same solver object.
+   * @param t the operator to compare to for equality
+   * @return true if the operators are equal
+   */
+  @Override public boolean equals(Object t)
+  {
+    if (this == t)
+      return true;
+    if (t == null || getClass() != t.getClass())
+      return false;
+    return equals(pointer, ((Op) t).getPointer());
+  }
+
+  private native boolean equals(long pointer1, long pointer2);
+
+  /**
+   * @return the kind of this operator
+   */
+  public Kind getKind()
+  {
+    try
+    {
+      int value = getKind(pointer);
+      return Kind.fromInt(value);
+    }
+    catch (CVC5ApiException e)
+    {
+      e.printStackTrace();
+      throw new RuntimeException(e.getMessage());
+    }
+  }
+
+  private native int getKind(long pointer);
+
+  /**
+   * @return true if this operator is a null term
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * @return true iff this operator is indexed
+   */
+  public boolean isIndexed()
+  {
+    return isIndexed(pointer);
+  }
+
+  private native boolean isIndexed(long pointer);
+
+  /**
+   * @return the number of indices of this op
+   */
+  public int getNumIndices()
+  {
+    return getNumIndices(pointer);
+  }
+
+  private native int getNumIndices(long pointer);
+
+  /**
+   * Get the indices used to create this Op.
+   * Check the Op Kind with getKind() to determine which argument to use.
+   *
+   * @return the indices used to create this Op
+   */
+  public int[] getIntegerIndices()
+  {
+    return getIntegerIndices(pointer);
+  }
+
+  private native int[] getIntegerIndices(long pointer);
+
+  /**
+   * Get the indices used to create this Op.
+   * Check the Op Kind with getKind() to determine which argument to use.
+   *
+   * @return the indices used to create this Op
+   */
+  public String[] getStringIndices()
+  {
+    return getStringIndices(pointer);
+  }
+
+  private native String[] getStringIndices(long pointer);
+
+  /**
+   * @return a string representation of this operator
+   */
+  protected native String toString(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/OptionInfo.java b/src/api/java/io/github/cvc5/api/OptionInfo.java
new file mode 100644 (file)
index 0000000..76633a8
--- /dev/null
@@ -0,0 +1,209 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Gereon Kremer, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.math.BigInteger;
+
+/**
+ * Holds some description about a particular option, including its name, its
+ * aliases, whether the option was explicitly set by the user, and information
+ * concerning its value. The `valueInfo` member holds any of the following
+ * alternatives:
+ * - VoidInfo if the option holds no value (or the value has no native type)
+ * - ValueInfo if the option is of type boolean or String, holds the
+ *   current value and the default value.
+ * - NumberInfo if the option is of type BigInteger or double, holds
+ *   the current and default value, as well as the minimum and maximum.
+ * - ModeInfo if the option is a mode option, holds the current and default
+ *   values, as well as a list of valid modes.
+ * Additionally, this class provides convenience functions to obtain the
+ * current value of an option in a type-safe manner using boolValue(),
+ * stringValue(), intValue(), and doubleValue(). They assert that
+ * the option has the respective type and return the current value.
+ */
+public class OptionInfo extends AbstractPointer
+{
+  // region construction and destruction
+  OptionInfo(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+    this.name = getName(pointer);
+    this.aliases = getAliases(pointer);
+    this.setByUser = getSetByUser(pointer);
+    this.baseInfo = getBaseInfo(pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  /**
+   * @return a string representation of this optionInfo.
+   */
+  protected native String toString(long pointer);
+
+  // endregion
+
+  /** Abstract class for OptionInfo values */
+  public abstract class BaseInfo
+  {
+  }
+
+  /** Has the current and the default value */
+  public abstract class ValueInfo<T> extends BaseInfo
+  {
+    private final T defaultValue;
+    private final T currentValue;
+    public ValueInfo(T defaultValue, T currentValue)
+    {
+      this.defaultValue = defaultValue;
+      this.currentValue = currentValue;
+    }
+    public T getDefaultValue()
+    {
+      return defaultValue;
+    }
+    public T getCurrentValue()
+    {
+      return currentValue;
+    }
+  }
+
+  public class ModeInfo extends ValueInfo<String>
+  {
+    private final String[] modes;
+
+    public ModeInfo(String defaultValue, String currentValue, String[] modes)
+    {
+      super(defaultValue, currentValue);
+      this.modes = modes;
+    }
+    public String[] getModes()
+    {
+      return modes;
+    }
+  }
+
+  /** Has no value information */
+  public class VoidInfo extends BaseInfo
+  {
+  }
+
+  /** Default value, current value, minimum and maximum of a numeric value */
+  public class NumberInfo<T> extends ValueInfo<T>
+  {
+    private final T minimum;
+    private final T maximum;
+    public NumberInfo(T defaultValue, T currentValue, T minimum, T maximum)
+    {
+      super(defaultValue, currentValue);
+      this.minimum = minimum;
+      this.maximum = maximum;
+    }
+    public T getMinimum()
+    {
+      return minimum;
+    }
+    public T getMaximum()
+    {
+      return maximum;
+    }
+  }
+
+  private native String getName(long pointer);
+
+  private native String[] getAliases(long pointer);
+
+  private native boolean getSetByUser(long pointer);
+
+  private native BaseInfo getBaseInfo(long pointer);
+
+  /** The option name */
+  private final String name;
+  public String getName()
+  {
+    return name;
+  }
+  /** The option name aliases */
+  private final String[] aliases;
+  public String[] getAliases()
+  {
+    return aliases;
+  }
+  /** Whether the option was explicitly set by the user */
+  private final boolean setByUser;
+  public boolean getSetByUser()
+  {
+    return setByUser;
+  }
+
+  /** The option variant information */
+  private final BaseInfo baseInfo;
+  public BaseInfo getBaseInfo()
+  {
+    return baseInfo;
+  }
+
+  /**
+   * Obtain the current value as a boolean. Asserts that valueInfo holds a boolean.
+   */
+  public boolean booleanValue()
+  {
+    return booleanValue(pointer);
+  }
+
+  private native boolean booleanValue(long pointer);
+
+  /**
+   * Obtain the current value as a string. Asserts that valueInfo holds a
+   * string.
+   */
+  public String stringValue()
+  {
+    return stringValue(pointer);
+  }
+
+  private native String stringValue(long pointer);
+
+  /**
+   * Obtain the current value as as int. Asserts that valueInfo holds an int.
+   */
+  public BigInteger intValue()
+  {
+    return intValue(pointer);
+  }
+
+  private native BigInteger intValue(long pointer);
+
+  /**
+   * Obtain the current value as a double. Asserts that valueInfo holds a
+   * double.
+   */
+  public double doubleValue()
+  {
+    return doubleValue(pointer);
+  }
+
+  private native double doubleValue(long pointer);
+};
diff --git a/src/api/java/io/github/cvc5/api/Pair.java b/src/api/java/io/github/cvc5/api/Pair.java
new file mode 100644 (file)
index 0000000..6ebd8c2
--- /dev/null
@@ -0,0 +1,39 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class Pair<K, V>
+{
+  public K first;
+  public V second;
+  public Pair(K first, V second)
+  {
+    this.first = first;
+    this.second = second;
+  }
+
+  @Override public boolean equals(Object pair)
+  {
+    if (this == pair)
+      return true;
+    if (pair == null || getClass() != pair.getClass())
+      return false;
+
+    Pair<K, V> p = (Pair<K, V>) pair;
+
+    return first.equals(p.first) && second.equals(p.second);
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/Result.java b/src/api/java/io/github/cvc5/api/Result.java
new file mode 100644 (file)
index 0000000..500ec7f
--- /dev/null
@@ -0,0 +1,208 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class Result extends AbstractPointer
+{
+  // region construction and destruction
+  Result(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  public enum UnknownExplanation {
+    REQUIRES_FULL_CHECK(0),
+    INCOMPLETE(1),
+    TIMEOUT(2),
+    RESOURCEOUT(3),
+    MEMOUT(4),
+    INTERRUPTED(5),
+    NO_STATUS(6),
+    UNSUPPORTED(7),
+    OTHER(8),
+    UNKNOWN_REASON(9);
+
+    /* the int value of the UnknownExplanation */
+    private int value;
+    private static Map<Integer, UnknownExplanation> explanationMap = new HashMap<>();
+    private UnknownExplanation(int value)
+    {
+      this.value = value;
+    }
+
+    static
+    {
+      for (UnknownExplanation explanation : UnknownExplanation.values())
+      {
+        explanationMap.put(explanation.getValue(), explanation);
+      }
+    }
+
+    public static UnknownExplanation fromInt(int value) throws CVC5ApiException
+    {
+      if (value < REQUIRES_FULL_CHECK.value || value > UNKNOWN_REASON.value)
+      {
+        throw new CVC5ApiException("UnknownExplanation value " + value
+            + " is outside the valid range [" + REQUIRES_FULL_CHECK.value + ","
+            + UNKNOWN_REASON.value + "]");
+      }
+      return explanationMap.get(value);
+    }
+
+    public int getValue()
+    {
+      return value;
+    }
+  }
+
+  /**
+   * Return true if Result is empty, i.e., a nullary Result, and not an actual
+   * result returned from a checkSat() (and friends) query.
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * Return true if query was a satisfiable checkSat() or checkSatAssuming()
+   * query.
+   */
+  public boolean isSat()
+  {
+    return isSat(pointer);
+  }
+
+  private native boolean isSat(long pointer);
+
+  /**
+   * Return true if query was an unsatisfiable checkSat() or
+   * checkSatAssuming() query.
+   */
+  public boolean isUnsat()
+  {
+    return isUnsat(pointer);
+  }
+
+  private native boolean isUnsat(long pointer);
+
+  /**
+   * Return true if query was a checkSat() or checkSatAssuming() query and
+   * cvc5 was not able to determine (un)satisfiability.
+   */
+  public boolean isSatUnknown()
+  {
+    return isSatUnknown(pointer);
+  }
+
+  private native boolean isSatUnknown(long pointer);
+
+  /**
+   * Return true if corresponding query was an entailed checkEntailed() query.
+   */
+  public boolean isEntailed()
+  {
+    return isEntailed(pointer);
+  }
+
+  private native boolean isEntailed(long pointer);
+
+  /**
+   * Return true if corresponding query was a checkEntailed() query that is
+   * not entailed.
+   */
+  public boolean isNotEntailed()
+  {
+    return isNotEntailed(pointer);
+  }
+
+  private native boolean isNotEntailed(long pointer);
+
+  /**
+   * Return true if query was a checkEntailed() query and cvc5 was not able to
+   * determine if it is entailed.
+   */
+  public boolean isEntailmentUnknown()
+  {
+    return isEntailmentUnknown(pointer);
+  }
+
+  private native boolean isEntailmentUnknown(long pointer);
+
+  /**
+   * Operator overloading for equality of two results.
+   * @param r the result to compare to for equality
+   * @return true if the results are equal
+   */
+  @Override public boolean equals(Object r)
+  {
+    if (this == r)
+      return true;
+    if (r == null || getClass() != r.getClass())
+      return false;
+    Result result = (Result) r;
+    if (this.pointer == result.pointer)
+    {
+      return true;
+    }
+    return equals(pointer, result.getPointer());
+  }
+
+  private native boolean equals(long pointer1, long pointer2);
+
+  /**
+   * @return an explanation for an unknown query result.
+   */
+  public UnknownExplanation getUnknownExplanation()
+  {
+    try
+    {
+      int explanation = getUnknownExplanation(pointer);
+      return UnknownExplanation.fromInt(explanation);
+    }
+    catch (CVC5ApiException e)
+    {
+      e.printStackTrace();
+      throw new RuntimeException(e.getMessage());
+    }
+  }
+
+  private native int getUnknownExplanation(long pointer);
+
+  /**
+   * @return a string representation of this result.
+   */
+  protected native String toString(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/RoundingMode.java b/src/api/java/io/github/cvc5/api/RoundingMode.java
new file mode 100644 (file)
index 0000000..ecc01c3
--- /dev/null
@@ -0,0 +1,63 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public enum RoundingMode {
+  /**
+   * Round to the nearest even number.
+   * If the two nearest floating-point numbers bracketing an unrepresentable
+   * infinitely precise result are equally near, the one with an even least
+   * significant digit will be delivered.
+   */
+  ROUND_NEAREST_TIES_TO_EVEN(0),
+  /**
+   * Round towards positive infinity (+oo).
+   * The result shall be the format’s floating-point number (possibly +oo)
+   * closest to and no less than the infinitely precise result.
+   */
+  ROUND_TOWARD_POSITIVE(1),
+  /**
+   * Round towards negative infinity (-oo).
+   * The result shall be the format’s floating-point number (possibly -oo)
+   * closest to and no less than the infinitely precise result.
+   */
+  ROUND_TOWARD_NEGATIVE(2),
+  /**
+   * Round towards zero.
+   * The result shall be the format’s floating-point number closest to and no
+   * greater in magnitude than the infinitely precise result.
+   */
+  ROUND_TOWARD_ZERO(3),
+  /**
+   * Round to the nearest number away from zero.
+   * If the two nearest floating-point numbers bracketing an unrepresentable
+   * infinitely precise result are equally near, the one with larger magnitude
+   * will be selected.
+   */
+  ROUND_NEAREST_TIES_TO_AWAY(4);
+
+  private int value;
+
+  private RoundingMode(int value)
+  {
+    this.value = value;
+  }
+
+  public int getValue()
+  {
+    return value;
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/Solver.java b/src/api/java/io/github/cvc5/api/Solver.java
new file mode 100644 (file)
index 0000000..670ab7c
--- /dev/null
@@ -0,0 +1,2654 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.io.IOException;
+import java.util.*;
+
+public class Solver implements IPointer
+{
+  private final long pointer;
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  private native long newSolver();
+
+  public void deletePointer()
+  {
+    deletePointer(pointer);
+  }
+
+  private static native void deletePointer(long pointer);
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  static
+  {
+    Utils.loadLibraries();
+  }
+
+  /* .................................................................... */
+  /* Constructors                                                         */
+  /* .................................................................... */
+
+  public Solver()
+  {
+    this.pointer = newSolver();
+  }
+
+  /* .................................................................... */
+  /* Sorts Handling                                                       */
+  /* .................................................................... */
+
+  /**
+   * @return sort null
+   */
+
+  public Sort getNullSort()
+  {
+    long sortPointer = getNullSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long getNullSort(long pointer);
+
+  /**
+   * @return sort Boolean
+   */
+  public Sort getBooleanSort()
+  {
+    long sortPointer = getBooleanSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long getBooleanSort(long pointer);
+
+  /**
+   * @return sort Integer (in cvc5, Integer is a subtype of Real)
+   */
+  public Sort getIntegerSort()
+  {
+    long sortPointer = getIntegerSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  public native long getIntegerSort(long pointer);
+  /**
+   * @return sort Real
+   */
+  public Sort getRealSort()
+  {
+    long sortPointer = getRealSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long getRealSort(long pointer);
+  /**
+   * @return sort RegExp
+   */
+  public Sort getRegExpSort()
+  {
+    long sortPointer = getRegExpSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long getRegExpSort(long pointer);
+  /**
+   * @return sort RoundingMode
+   */
+  public Sort getRoundingModeSort() throws CVC5ApiException
+  {
+    long sortPointer = getRoundingModeSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long getRoundingModeSort(long pointer) throws CVC5ApiException;
+  /**
+   * @return sort String
+   */
+  public Sort getStringSort()
+  {
+    long sortPointer = getStringSort(pointer);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long getStringSort(long solverPointer);
+  /**
+   * Create an array sort.
+   * @param indexSort the array index sort
+   * @param elemSort the array element sort
+   * @return the array sort
+   */
+  public Sort mkArraySort(Sort indexSort, Sort elemSort)
+  {
+    long sortPointer = mkArraySort(pointer, indexSort.getPointer(), elemSort.getPointer());
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkArraySort(long pointer, long indexSortPointer, long elementSortPointer);
+
+  /**
+   * Create a bit-vector sort.
+   * @param size the bit-width of the bit-vector sort
+   * @return the bit-vector sort
+   */
+  public Sort mkBitVectorSort(int size) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(size, "size");
+    long sortPointer = mkBitVectorSort(pointer, size);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkBitVectorSort(long pointer, int size);
+
+  /**
+   * Create a floating-point sort.
+   * @param exp the bit-width of the exponent of the floating-point sort.
+   * @param sig the bit-width of the significand of the floating-point sort.
+   */
+  public Sort mkFloatingPointSort(int exp, int sig) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long sortPointer = mkFloatingPointSort(pointer, exp, sig);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkFloatingPointSort(long solverPointer, int exp, int sig);
+
+  /**
+   * Create a datatype sort.
+   * @param dtypedecl the datatype declaration from which the sort is
+   *     created
+   * @return the datatype sort
+   */
+  public Sort mkDatatypeSort(DatatypeDecl dtypedecl) throws CVC5ApiException
+  {
+    long pointer = mkDatatypeSort(this.pointer, dtypedecl.getPointer());
+    return new Sort(this, pointer);
+  }
+
+  private native long mkDatatypeSort(long pointer, long datatypeDeclPointer)
+      throws CVC5ApiException;
+
+  /**
+   * Create a vector of datatype sorts. The names of the datatype
+   * declarations must be distinct.
+   *
+   * @param dtypedecls the datatype declarations from which the sort is
+   *     created
+   * @return the datatype sorts
+   */
+  public Sort[] mkDatatypeSorts(List<DatatypeDecl> dtypedecls) throws CVC5ApiException
+  {
+    return mkDatatypeSorts(dtypedecls.toArray(new DatatypeDecl[0]));
+  }
+
+  /**
+   * Create a vector of datatype sorts. The names of the datatype
+   * declarations must be distinct.
+   *
+   * @param dtypedecls the datatype declarations from which the sort is
+   *     created
+   * @return the datatype sorts
+   */
+  public Sort[] mkDatatypeSorts(DatatypeDecl[] dtypedecls) throws CVC5ApiException
+  {
+    long[] declPointers = Utils.getPointers(dtypedecls);
+    long[] sortPointers = mkDatatypeSorts(pointer, declPointers);
+    Sort[] sorts = Utils.getSorts(this, sortPointers);
+    return sorts;
+  }
+
+  private native long[] mkDatatypeSorts(long pointer, long[] declPointers) throws CVC5ApiException;
+
+  /**
+   * Create a vector of datatype sorts using unresolved sorts. The names of
+   * the datatype declarations in dtypedecls must be distinct.
+   *
+   * This method is called when the DatatypeDecl objects dtypedecls have
+   * been built using "unresolved" sorts.
+   *
+   * We associate each sort in unresolvedSorts with exacly one datatype from
+   * dtypedecls. In particular, it must have the same name as exactly one
+   * datatype declaration in dtypedecls.
+   *
+   * When constructing datatypes, unresolved sorts are replaced by the
+   * datatype sort constructed for the datatype declaration it is associated
+   * with.
+   *
+   * @param dtypedecls the datatype declarations from which the sort is
+   *     created
+   * @param unresolvedSorts the set of unresolved sorts
+   * @return the datatype sorts
+   */
+  public List<Sort> mkDatatypeSorts(List<DatatypeDecl> dtypedecls, Set<Sort> unresolvedSorts)
+      throws CVC5ApiException
+  {
+    Sort[] array = mkDatatypeSorts(
+        dtypedecls.toArray(new DatatypeDecl[0]), unresolvedSorts.toArray(new Sort[0]));
+    return Arrays.asList(array);
+  }
+
+  /**
+   * Create a vector of datatype sorts using unresolved sorts. The names of
+   * the datatype declarations in dtypedecls must be distinct.
+   *
+   * This method is called when the DatatypeDecl objects dtypedecls have
+   * been built using "unresolved" sorts.
+   *
+   * We associate each sort in unresolvedSorts with exacly one datatype from
+   * dtypedecls. In particular, it must have the same name as exactly one
+   * datatype declaration in dtypedecls.
+   *
+   * When constructing datatypes, unresolved sorts are replaced by the
+   * datatype sort constructed for the datatype declaration it is associated
+   * with.
+   *
+   * @param dtypedecls the datatype declarations from which the sort is
+   *     created
+   * @param unresolvedSorts the list of unresolved sorts
+   * @return the datatype sorts
+   */
+  public Sort[] mkDatatypeSorts(DatatypeDecl[] dtypedecls, Sort[] unresolvedSorts)
+      throws CVC5ApiException
+  {
+    long[] declPointers = Utils.getPointers(dtypedecls);
+    long[] unresolvedPointers = Utils.getPointers(unresolvedSorts);
+    long[] sortPointers = mkDatatypeSorts(pointer, declPointers, unresolvedPointers);
+    Sort[] sorts = Utils.getSorts(this, sortPointers);
+    return sorts;
+  }
+
+  private native long[] mkDatatypeSorts(
+      long pointer, long[] declPointers, long[] unresolvedPointers) throws CVC5ApiException;
+
+  /**
+   * Create function sort.
+   * @param domain the sort of the fuction argument
+   * @param codomain the sort of the function return value
+   * @return the function sort
+   */
+  public Sort mkFunctionSort(Sort domain, Sort codomain)
+  {
+    long sortPointer = mkFunctionSort(pointer, domain.getPointer(), codomain.getPointer());
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkFunctionSort(long pointer, long domainPointer, long codomainPointer);
+
+  /**
+   * Create function sort.
+   * @param sorts the sort of the function arguments
+   * @param codomain the sort of the function return value
+   * @return the function sort
+   */
+  public Sort mkFunctionSort(Sort[] sorts, Sort codomain)
+  {
+    long sortPointer = mkFunctionSort(pointer, Utils.getPointers(sorts), codomain.getPointer());
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkFunctionSort(long pointer, long[] sortPointers, long codomainPointer);
+
+  /**
+   * Create a sort parameter.
+   * @param symbol the name of the sort
+   * @return the sort parameter
+   */
+  public Sort mkParamSort(String symbol)
+  {
+    long sortPointer = mkParamSort(pointer, symbol);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkParamSort(long pointer, String symbol);
+
+  /**
+   * Create a predicate sort.
+   * @param sorts the list of sorts of the predicate
+   * @return the predicate sort
+   */
+  public Sort mkPredicateSort(Sort[] sorts)
+  {
+    long sortPointer = mkPredicateSort(pointer, Utils.getPointers(sorts));
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkPredicateSort(long pointer, long[] sortPointers);
+
+  /**
+   * Create a record sort
+   * @param fields the list of fields of the record
+   * @return the record sort
+   */
+  public Sort mkRecordSort(Pair<String, Sort>[] fields)
+  {
+    long sortPointer = mkRecordSort(pointer, Utils.getPairs(fields));
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkRecordSort(long pointer, Pair<String, Long>[] fields);
+
+  /**
+   * Create a set sort.
+   * @param elemSort the sort of the set elements
+   * @return the set sort
+   */
+  public Sort mkSetSort(Sort elemSort)
+  {
+    long sortPointer = mkSetSort(pointer, elemSort.getPointer());
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkSetSort(long pointer, long elemSortPointer);
+  /**
+   * Create a bag sort.
+   * @param elemSort the sort of the bag elements
+   * @return the bag sort
+   */
+  public Sort mkBagSort(Sort elemSort)
+  {
+    long sortPointer = mkBagSort(pointer, elemSort.getPointer());
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkBagSort(long pointer, long elemSortPointer);
+
+  /**
+   * Create a sequence sort.
+   * @param elemSort the sort of the sequence elements
+   * @return the sequence sort
+   */
+  public Sort mkSequenceSort(Sort elemSort)
+  {
+    long sortPointer = mkSequenceSort(pointer, elemSort.getPointer());
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkSequenceSort(long pointer, long elemSortPointer);
+
+  /**
+   * Create an uninterpreted sort.
+   * @param symbol the name of the sort
+   * @return the uninterpreted sort
+   */
+  public Sort mkUninterpretedSort(String symbol)
+  {
+    long sortPointer = mkUninterpretedSort(pointer, symbol);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkUninterpretedSort(long pointer, String symbol);
+
+  /**
+   * Create a sort constructor sort.
+   * @param symbol the symbol of the sort
+   * @param arity the arity of the sort
+   * @return the sort constructor sort
+   */
+  public Sort mkSortConstructorSort(String symbol, int arity) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(arity, "arity");
+    long sortPointer = mkSortConstructorSort(pointer, symbol, arity);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkSortConstructorSort(long pointer, String symbol, int arity);
+
+  /**
+   * Create a tuple sort.
+   * @param sorts of the elements of the tuple
+   * @return the tuple sort
+   */
+  public Sort mkTupleSort(Sort[] sorts)
+  {
+    long[] sortPointers = Utils.getPointers(sorts);
+    long sortPointer = mkTupleSort(pointer, sortPointers);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long mkTupleSort(long pointer, long[] sortPointers);
+
+  /* .................................................................... */
+  /* Create Terms                                                         */
+  /* .................................................................... */
+
+  /**
+   * Create 0-ary term of given kind.
+   * @param kind the kind of the term
+   * @return the Term
+   */
+  public Term mkTerm(Kind kind)
+  {
+    long termPointer = mkTerm(pointer, kind.getValue());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, int kindValue);
+
+  /**
+   * Create a unary term of given kind.
+   * @param kind the kind of the term
+   * @param child the child of the term
+   * @return the Term
+   */
+  public Term mkTerm(Kind kind, Term child)
+  {
+    long termPointer = mkTerm(pointer, kind.getValue(), child.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, int kindValue, long childPointer);
+
+  /**
+   * Create binary term of given kind.
+   * @param kind the kind of the term
+   * @param child1 the first child of the term
+   * @param child2 the second child of the term
+   * @return the Term
+   */
+  public Term mkTerm(Kind kind, Term child1, Term child2)
+  {
+    long termPointer = mkTerm(pointer, kind.getValue(), child1.getPointer(), child2.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, int kindValue, long child1Pointer, long child2Pointer);
+
+  /**
+   * Create ternary term of given kind.
+   * @param kind the kind of the term
+   * @param child1 the first child of the term
+   * @param child2 the second child of the term
+   * @param child3 the third child of the term
+   * @return the Term
+   */
+  public Term mkTerm(Kind kind, Term child1, Term child2, Term child3)
+  {
+    long termPointer = mkTerm(
+        pointer, kind.getValue(), child1.getPointer(), child2.getPointer(), child3.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(
+      long pointer, int kindValue, long child1Pointer, long child2Pointer, long child3Pointer);
+  /**
+   * Create n-ary term of given kind.
+   * @param kind the kind of the term
+   * @param children the children of the term
+   * @return the Term
+   */
+  public Term mkTerm(Kind kind, Term[] children)
+  {
+    long[] childPointers = Utils.getPointers(children);
+    long termPointer = mkTerm(pointer, kind.getValue(), childPointers);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, int kindValue, long[] childrenPointers);
+
+  /**
+   * Create nullary term of given kind from a given operator.
+   * Create operators with mkOp().
+   * @param op the operator
+   * @return the Term
+   */
+  public Term mkTerm(Op op)
+  {
+    long termPointer = mkTerm(pointer, op.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, long opPointer);
+  /**
+   * Create unary term of given kind from a given operator.
+   * Create operators with mkOp().
+   * @param op the operator
+   * @param child the child of the term
+   * @return the Term
+   */
+  public Term mkTerm(Op op, Term child)
+  {
+    long termPointer = mkTerm(pointer, op.getPointer(), child.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, long opPointer, long childPointer);
+
+  /**
+   * Create binary term of given kind from a given operator.
+   * Create operators with mkOp().
+   * @param op the operator
+   * @param child1 the first child of the term
+   * @param child2 the second child of the term
+   * @return the Term
+   */
+  public Term mkTerm(Op op, Term child1, Term child2)
+  {
+    long termPointer = mkTerm(pointer, op.getPointer(), child1.getPointer(), child2.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, long opPointer, long child1Pointer, long child2Pointer);
+  /**
+   * Create ternary term of given kind from a given operator.
+   * Create operators with mkOp().
+   * @param op the operator
+   * @param child1 the first child of the term
+   * @param child2 the second child of the term
+   * @param child3 the third child of the term
+   * @return the Term
+   */
+  public Term mkTerm(Op op, Term child1, Term child2, Term child3)
+  {
+    long termPointer =
+        mkTerm(op.getPointer(), child1.getPointer(), child2.getPointer(), child3.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(
+      long pointer, long opPointer, long child1Pointer, long child2Pointer, long child3Pointer);
+
+  /**
+   * Create n-ary term of given kind from a given operator.
+   * Create operators with mkOp().
+   * @param op the operator
+   * @param children the children of the term
+   * @return the Term
+   */
+  public Term mkTerm(Op op, List<Term> children)
+  {
+    return mkTerm(op, children.toArray(new Term[0]));
+  }
+
+  /**
+   * Create n-ary term of given kind from a given operator.
+   * Create operators with mkOp().
+   * @param op the operator
+   * @param children the children of the term
+   * @return the Term
+   */
+  public Term mkTerm(Op op, Term[] children)
+  {
+    long[] childPointers = Utils.getPointers(children);
+    long termPointer = mkTerm(pointer, op.getPointer(), childPointers);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTerm(long pointer, long opPointer, long[] childrenPointers);
+
+  /**
+   * Create a tuple term. Terms are automatically converted if sorts are
+   * compatible.
+   * @param sorts The sorts of the elements in the tuple
+   * @param terms The elements in the tuple
+   * @return the tuple Term
+   */
+  public Term mkTuple(Sort[] sorts, Term[] terms)
+  {
+    long[] sortPointers = Utils.getPointers(sorts);
+    long[] termPointers = Utils.getPointers(terms);
+    long termPointer = mkTuple(pointer, sortPointers, termPointers);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTuple(long pointer, long[] sortPointers, long[] termPointers);
+
+  /* .................................................................... */
+  /* Create Operators                                                     */
+  /* .................................................................... */
+
+  /**
+   * Create an operator for a builtin Kind
+   * The Kind may not be the Kind for an indexed operator
+   *   (e.g. BITVECTOR_EXTRACT)
+   * Note: in this case, the Op simply wraps the Kind.
+   * The Kind can be used in mkTerm directly without
+   *   creating an op first.
+   * @param kind the kind to wrap
+   */
+  public Op mkOp(Kind kind)
+  {
+    long opPointer = mkOp(pointer, kind.getValue());
+    return new Op(this, opPointer);
+  }
+
+  private native long mkOp(long pointer, int kindValue);
+  /**
+   * Create operator of kind:
+   *   - RECORD_UPDATE
+   *   - DIVISIBLE (to support arbitrary precision integers)
+   * See enum Kind for a description of the parameters.
+   * @param kind the kind of the operator
+   * @param arg the string argument to this operator
+   */
+  public Op mkOp(Kind kind, String arg)
+  {
+    long opPointer = mkOp(pointer, kind.getValue(), arg);
+    return new Op(this, opPointer);
+  }
+
+  private native long mkOp(long pointer, int kindValue, String arg);
+
+  /**
+   * Create operator of kind:
+   *   - DIVISIBLE
+   *   - BITVECTOR_REPEAT
+   *   - BITVECTOR_ZERO_EXTEND
+   *   - BITVECTOR_SIGN_EXTEND
+   *   - BITVECTOR_ROTATE_LEFT
+   *   - BITVECTOR_ROTATE_RIGHT
+   *   - INT_TO_BITVECTOR
+   *   - FLOATINGPOINT_TO_UBV
+   *   - FLOATINGPOINT_TO_UBV_TOTAL
+   *   - FLOATINGPOINT_TO_SBV
+   *   - FLOATINGPOINT_TO_SBV_TOTAL
+   *   - TUPLE_UPDATE
+   * See enum Kind for a description of the parameters.
+   * @param kind the kind of the operator
+   * @param arg the unsigned int argument to this operator
+   */
+  public Op mkOp(Kind kind, int arg) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(arg, "arg");
+    long opPointer = mkOp(pointer, kind.getValue(), arg);
+    return new Op(this, opPointer);
+  }
+
+  private native long mkOp(long pointer, int kindValue, int arg);
+
+  /**
+   * Create operator of Kind:
+   *   - BITVECTOR_EXTRACT
+   *   - FLOATINGPOINT_TO_FP_IEEE_BITVECTOR
+   *   - FLOATINGPOINT_TO_FP_FLOATINGPOINT
+   *   - FLOATINGPOINT_TO_FP_REAL
+   *   - FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR
+   *   - FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR
+   *   - FLOATINGPOINT_TO_FP_GENERIC
+   * See enum Kind for a description of the parameters.
+   * @param kind the kind of the operator
+   * @param arg1 the first unsigned int argument to this operator
+   * @param arg2 the second unsigned int argument to this operator
+   */
+  public Op mkOp(Kind kind, int arg1, int arg2) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(arg1, "arg1");
+    Utils.validateUnsigned(arg2, "arg2");
+    long opPointer = mkOp(pointer, kind.getValue(), arg1, arg2);
+    return new Op(this, opPointer);
+  }
+
+  private native long mkOp(long pointer, int kindValue, int arg1, int arg2);
+
+  /**
+   * Create operator of Kind:
+   *   - TUPLE_PROJECT
+   * See enum Kind for a description of the parameters.
+   * @param kind the kind of the operator
+   * @param args the arguments (indices) of the operator
+   */
+  public Op mkOp(Kind kind, int[] args) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(args, "args");
+    long opPointer = mkOp(pointer, kind.getValue(), args);
+    return new Op(this, opPointer);
+  }
+
+  private native long mkOp(long pointer, int kindValue, int[] args);
+
+  /* .................................................................... */
+  /* Create Constants                                                     */
+  /* .................................................................... */
+
+  /**
+   * Create a Boolean true constant.
+   * @return the true constant
+   */
+  public Term mkTrue()
+  {
+    long termPointer = mkTrue(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkTrue(long pointer);
+  /**
+   * Create a Boolean false constant.
+   * @return the false constant
+   */
+  public Term mkFalse()
+  {
+    long termPointer = mkFalse(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkFalse(long pointer);
+  /**
+   * Create a Boolean constant.
+   * @return the Boolean constant
+   * @param val the value of the constant
+   */
+  public Term mkBoolean(boolean val)
+  {
+    long termPointer = mkBoolean(pointer, val);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkBoolean(long pointer, boolean val);
+  /**
+   * Create a constant representing the number Pi.
+   * @return a constant representing Pi
+   */
+  public Term mkPi()
+  {
+    long termPointer = mkPi(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkPi(long pointer);
+  /**
+   * Create an integer constant from a string.
+   * @param s the string representation of the constant, may represent an
+   *          integer (e.g., "123").
+   * @return a constant of sort Integer assuming 's' represents an integer)
+   */
+  public Term mkInteger(String s) throws CVC5ApiException
+  {
+    long termPointer = mkInteger(pointer, s);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkInteger(long pointer, String s) throws CVC5ApiException;
+
+  /**
+   * Create an integer constant from a c++ int.
+   * @param val the value of the constant
+   * @return a constant of sort Integer
+   */
+  public Term mkInteger(long val)
+  {
+    long termPointer = mkInteger(pointer, val);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkInteger(long pointer, long val);
+  /**
+   * Create a real constant from a string.
+   * @param s the string representation of the constant, may represent an
+   *          integer (e.g., "123") or real constant (e.g., "12.34" or
+   * "12/34").
+   * @return a constant of sort Real
+   */
+  public Term mkReal(String s) throws CVC5ApiException
+  {
+    long termPointer = mkReal(pointer, s);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkReal(long pointer, String s) throws CVC5ApiException;
+  /**
+   * Create a real constant from an integer.
+   * @param val the value of the constant
+   * @return a constant of sort Integer
+   */
+  public Term mkReal(long val)
+  {
+    long termPointer = mkRealValue(pointer, val);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkRealValue(long pointer, long val);
+  /**
+   * Create a real constant from a rational.
+   * @param num the value of the numerator
+   * @param den the value of the denominator
+   * @return a constant of sort Real
+   */
+  public Term mkReal(long num, long den)
+  {
+    long termPointer = mkReal(pointer, num, den);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkReal(long pointer, long num, long den);
+
+  /**
+   * Create a regular expression empty term.
+   * @return the empty term
+   */
+  public Term mkRegexpEmpty()
+  {
+    long termPointer = mkRegexpEmpty(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkRegexpEmpty(long pointer);
+
+  /**
+   * Create a regular expression sigma term.
+   * @return the sigma term
+   */
+  public Term mkRegexpSigma()
+  {
+    long termPointer = mkRegexpSigma(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkRegexpSigma(long pointer);
+
+  /**
+   * Create a constant representing an empty set of the given sort.
+   * @param sort the sort of the set elements.
+   * @return the empty set constant
+   */
+  public Term mkEmptySet(Sort sort)
+  {
+    long termPointer = mkEmptySet(pointer, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkEmptySet(long pointer, long sortPointer);
+  /**
+   * Create a constant representing an empty bag of the given sort.
+   * @param sort the sort of the bag elements.
+   * @return the empty bag constant
+   */
+  public Term mkEmptyBag(Sort sort)
+  {
+    long termPointer = mkEmptyBag(pointer, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkEmptyBag(long pointer, long sortPointer);
+
+  /**
+   * Create a separation logic empty term.
+   * @return the separation logic empty term
+   */
+  public Term mkSepEmp()
+  {
+    long termPointer = mkSepEmp(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkSepEmp(long pointer);
+
+  /**
+   * Create a separation logic nil term.
+   * @param sort the sort of the nil term
+   * @return the separation logic nil term
+   */
+  public Term mkSepNil(Sort sort)
+  {
+    long termPointer = mkSepNil(pointer, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkSepNil(long pointer, long sortPointer);
+
+  /**
+   * Create a String constant.
+   * @param s the string this constant represents
+   * @return the String constant
+   */
+  public Term mkString(String s)
+  {
+    return mkString(s, false);
+  }
+
+  /**
+   * Create a String constant.
+   * @param s the string this constant represents
+   * @param useEscSequences determines whether escape sequences in `s`
+   * should be converted to the corresponding unicode character
+   * @return the String constant
+   */
+  public Term mkString(String s, boolean useEscSequences)
+  {
+    // TODO: review unicode
+    long termPointer = mkString(pointer, s, useEscSequences);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkString(long pointer, String s, boolean useEscSequences);
+
+  /**
+   * Create a String constant.
+   * @param s a list of unsigned (unicode) values this constant represents
+   *     as
+   * string
+   * @return the String constant
+   */
+  public Term mkString(int[] s) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(s, "s");
+    long termPointer = mkString(pointer, s);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkString(long pointer, int[] s);
+
+  /**
+   * Create an empty sequence of the given element sort.
+   * @param sort The element sort of the sequence.
+   * @return the empty sequence with given element sort.
+   */
+  public Term mkEmptySequence(Sort sort)
+  {
+    long termPointer = mkEmptySequence(pointer, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkEmptySequence(long pointer, long sortPointer);
+
+  /**
+   * Create a universe set of the given sort.
+   * @param sort the sort of the set elements
+   * @return the universe set constant
+   */
+  public Term mkUniverseSet(Sort sort)
+  {
+    long termPointer = mkUniverseSet(pointer, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkUniverseSet(long pointer, long sortPointer);
+
+  /**
+   * Create a bit-vector constant of given size and value = 0.
+   * @param size the bit-width of the bit-vector sort
+   * @return the bit-vector constant
+   */
+  public Term mkBitVector(int size) throws CVC5ApiException
+  {
+    return mkBitVector(size, 0);
+  }
+
+  /**
+   * Create a bit-vector constant of given size and value.
+   *
+   * Note: The given value must fit into a bit-vector of the given size.
+   *
+   * @param size the bit-width of the bit-vector sort
+   * @param val the value of the constant
+   * @return the bit-vector constant
+   */
+  public Term mkBitVector(int size, long val) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(size, "size");
+    Utils.validateUnsigned(val, "val");
+    long termPointer = mkBitVector(pointer, size, val);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkBitVector(long pointer, int size, long val);
+
+  /**
+   * Create a bit-vector constant of a given bit-width from a given string of
+   * base 2, 10 or 16.
+   *
+   * Note: The given value must fit into a bit-vector of the given size.
+   *
+   * @param size the bit-width of the constant
+   * @param s the string representation of the constant
+   * @param base the base of the string representation (2, 10, or 16)
+   * @return the bit-vector constant
+   */
+  public Term mkBitVector(int size, String s, int base) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(size, "size");
+    Utils.validateUnsigned(base, "base");
+    long termPointer = mkBitVector(pointer, size, s, base);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkBitVector(long pointer, int size, String s, int base);
+
+  /**
+   * Create a constant array with the provided constant value stored at
+   * every index
+   * @param sort the sort of the constant array (must be an array sort)
+   * @param val the constant value to store (must match the sort's element
+   *     sort)
+   * @return the constant array term
+   */
+  public Term mkConstArray(Sort sort, Term val)
+  {
+    long termPointer = mkConstArray(pointer, sort.getPointer(), val.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkConstArray(long pointer, long sortPointer, long valPointer);
+  /**
+   * Create a positive infinity floating-point constant.
+   * @param exp Number of bits in the exponent
+   * @param sig Number of bits in the significand
+   * @return the floating-point constant
+   */
+  public Term mkPosInf(int exp, int sig) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long termPointer = mkPosInf(pointer, exp, sig);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkPosInf(long pointer, int exp, int sig);
+  /**
+   * Create a negative infinity floating-point constant.
+   * @param exp Number of bits in the exponent
+   * @param sig Number of bits in the significand
+   * @return the floating-point constant
+   */
+  public Term mkNegInf(int exp, int sig) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long termPointer = mkNegInf(pointer, exp, sig);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkNegInf(long pointer, int exp, int sig);
+  /**
+   * Create a not-a-number (NaN) floating-point constant.
+   * @param exp Number of bits in the exponent
+   * @param sig Number of bits in the significand
+   * @return the floating-point constant
+   */
+  public Term mkNaN(int exp, int sig) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long termPointer = mkNaN(pointer, exp, sig);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkNaN(long pointer, int exp, int sig);
+
+  /**
+   * Create a positive zero (+0.0) floating-point constant.
+   * @param exp Number of bits in the exponent
+   * @param sig Number of bits in the significand
+   * @return the floating-point constant
+   */
+  public Term mkPosZero(int exp, int sig) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long termPointer = mkPosZero(pointer, exp, sig);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkPosZero(long pointer, int exp, int sig);
+
+  /**
+   * Create a negative zero (-0.0) floating-point constant.
+   * @param exp Number of bits in the exponent
+   * @param sig Number of bits in the significand
+   * @return the floating-point constant
+   */
+  public Term mkNegZero(int exp, int sig) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long termPointer = mkNegZero(pointer, exp, sig);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkNegZero(long pointer, int exp, int sig);
+
+  /**
+   * Create a roundingmode constant.
+   * @param rm the floating point rounding mode this constant represents
+   */
+  public Term mkRoundingMode(RoundingMode rm)
+  {
+    long termPointer = mkRoundingMode(pointer, rm.getValue());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkRoundingMode(long pointer, int rm);
+
+  /**
+   * Create uninterpreted constant.
+   * @param sort Sort of the constant
+   * @param index Index of the constant
+   */
+  public Term mkUninterpretedConst(Sort sort, int index) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(index, "index");
+    long termPointer = mkUninterpretedConst(pointer, sort.getPointer(), index);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkUninterpretedConst(long pointer, long sortPointer, int index);
+
+  /**
+   * Create an abstract value constant.
+   * @param index Index of the abstract value
+   */
+  public Term mkAbstractValue(String index)
+  {
+    long termPointer = mkAbstractValue(pointer, index);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkAbstractValue(long pointer, String index);
+
+  /**
+   * Create an abstract value constant.
+   * @param index Index of the abstract value
+   */
+  public Term mkAbstractValue(long index) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(index, "index");
+    long termPointer = mkAbstractValue(pointer, index);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkAbstractValue(long pointer, long index);
+
+  /**
+   * Create a floating-point constant.
+   * @param exp Size of the exponent
+   * @param sig Size of the significand
+   * @param val Value of the floating-point constant as a bit-vector term
+   */
+  public Term mkFloatingPoint(int exp, int sig, Term val) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(exp, "exp");
+    Utils.validateUnsigned(sig, "sig");
+    long termPointer = mkFloatingPoint(pointer, exp, sig, val.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkFloatingPoint(long pointer, int exp, int sig, long valPointer);
+
+  /* .................................................................... */
+  /* Create Variables                                                     */
+  /* .................................................................... */
+
+  /**
+   * Create (first-order) constant (0-arity function symbol).
+   * SMT-LIB:
+   * {@code
+   *   ( declare-const <symbol> <sort> )
+   *   ( declare-fun <symbol> ( ) <sort> )
+   * }
+   *
+   * @param sort the sort of the constant
+   * @param symbol the name of the constant
+   * @return the first-order constant
+   */
+  public Term mkConst(Sort sort, String symbol)
+  {
+    long termPointer = mkConst(pointer, sort.getPointer(), symbol);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkConst(long pointer, long sortPointer, String symbol);
+
+  /**
+   * Create (first-order) constant (0-arity function symbol), with a default
+   * symbol name.
+   *
+   * @param sort the sort of the constant
+   * @return the first-order constant
+   */
+  public Term mkConst(Sort sort)
+  {
+    long termPointer = mkConst(pointer, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long mkConst(long pointer, long sortPointer);
+
+  /**
+   * Create a bound variable to be used in a binder (i.e. a quantifier, a
+   * lambda, or a witness binder).
+   * @param sort the sort of the variable
+   * @return the variable
+   */
+  public Term mkVar(Sort sort)
+  {
+    return mkVar(sort, "");
+  }
+
+  /**
+   * Create a bound variable to be used in a binder (i.e. a quantifier, a
+   * lambda, or a witness binder).
+   * @param sort the sort of the variable
+   * @param symbol the name of the variable
+   * @return the variable
+   */
+  public Term mkVar(Sort sort, String symbol)
+  {
+    long termPointer = mkVar(pointer, sort.getPointer(), symbol);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkVar(long pointer, long sortPointer, String symbol);
+
+  /* .................................................................... */
+  /* Create datatype constructor declarations                             */
+  /* .................................................................... */
+
+  public DatatypeConstructorDecl mkDatatypeConstructorDecl(String name)
+  {
+    long declPointer = mkDatatypeConstructorDecl(pointer, name);
+    return new DatatypeConstructorDecl(this, declPointer);
+  }
+
+  private native long mkDatatypeConstructorDecl(long pointer, String name);
+
+  /* .................................................................... */
+  /* Create datatype declarations                                         */
+  /* .................................................................... */
+
+  /**
+   * Create a datatype declaration.
+   * @param name the name of the datatype
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name)
+  {
+    return mkDatatypeDecl(name, false);
+  }
+
+  /**
+   * Create a datatype declaration.
+   * @param name the name of the datatype
+   * @param isCoDatatype true if a codatatype is to be constructed
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name, boolean isCoDatatype)
+  {
+    long declPointer = mkDatatypeDecl(pointer, name, isCoDatatype);
+    return new DatatypeDecl(this, declPointer);
+  }
+
+  private native long mkDatatypeDecl(long pointer, String name, boolean isCoDatatype);
+
+  /**
+   * Create a datatype declaration.
+   * Create sorts parameter with Solver::mkParamSort().
+   * @param name the name of the datatype
+   * @param param the sort parameter
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name, Sort param)
+  {
+    return mkDatatypeDecl(name, param, false);
+  }
+
+  /**
+   * Create a datatype declaration.
+   * Create sorts parameter with Solver::mkParamSort().
+   * @param name the name of the datatype
+   * @param param the sort parameter
+   * @param isCoDatatype true if a codatatype is to be constructed
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name, Sort param, boolean isCoDatatype)
+  {
+    long declPointer = mkDatatypeDecl(pointer, name, param.getPointer(), isCoDatatype);
+    return new DatatypeDecl(this, declPointer);
+  }
+
+  private native long mkDatatypeDecl(
+      long pointer, String name, long paramPointer, boolean isCoDatatype);
+
+  /**
+   * Create a datatype declaration.
+   * Create sorts parameter with Solver::mkParamSort().
+   * @param name the name of the datatype
+   * @param params a list of sort parameters
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name, List<Sort> params)
+  {
+    return mkDatatypeDecl(name, params.toArray(new Sort[0]));
+  }
+
+  /**
+   * Create a datatype declaration.
+   * Create sorts parameter with Solver::mkParamSort().
+   * @param name the name of the datatype
+   * @param params a list of sort parameters
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name, Sort[] params)
+  {
+    return mkDatatypeDecl(name, params, false);
+  }
+
+  /**
+   * Create a datatype declaration.
+   * Create sorts parameter with Solver::mkParamSort().
+   * @param name the name of the datatype
+   * @param params a list of sort parameters
+   * @param isCoDatatype true if a codatatype is to be constructed
+   * @return the DatatypeDecl
+   */
+  public DatatypeDecl mkDatatypeDecl(String name, Sort[] params, boolean isCoDatatype)
+  {
+    long[] paramPointers = Utils.getPointers(params);
+    long declPointer = mkDatatypeDecl(pointer, name, paramPointers, isCoDatatype);
+    return new DatatypeDecl(this, declPointer);
+  }
+
+  private native long mkDatatypeDecl(
+      long pointer, String name, long[] paramPointers, boolean isCoDatatype);
+
+  /* .................................................................... */
+  /* Formula Handling                                                     */
+  /* .................................................................... */
+
+  /**
+   * Simplify a formula without doing "much" work.  Does not involve
+   * the SAT Engine in the simplification, but uses the current
+   * definitions, assertions, and the current partial model, if one
+   * has been constructed.  It also involves theory normalization.
+   * @param t the formula to simplify
+   * @return the simplified formula
+   */
+  public Term simplify(Term t)
+  {
+    long termPointer = simplify(pointer, t.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long simplify(long pointer, long termPointer);
+
+  /**
+   * Assert a formula.
+   * SMT-LIB:
+   * {@code
+   *   ( assert <term> )
+   * }
+   * @param term the formula to assert
+   */
+  public void assertFormula(Term term)
+  {
+    assertFormula(pointer, term.getPointer());
+  }
+
+  private native void assertFormula(long pointer, long termPointer);
+
+  /**
+   * Check satisfiability.
+   * SMT-LIB:
+   * {@code
+   *   ( check-sat )
+   * }
+   * @return the result of the satisfiability check.
+   */
+  public Result checkSat()
+  {
+    long resultPointer = checkSat(pointer);
+    return new Result(this, resultPointer);
+  }
+
+  private native long checkSat(long pointer);
+  /**
+   * Check satisfiability assuming the given formula.
+   * SMT-LIB:
+   * {@code
+   *   ( check-sat-assuming ( <prop_literal> ) )
+   * }
+   * @param assumption the formula to assume
+   * @return the result of the satisfiability check.
+   */
+  public Result checkSatAssuming(Term assumption)
+  {
+    long resultPointer = checkSatAssuming(pointer, assumption.getPointer());
+    return new Result(this, resultPointer);
+  }
+
+  private native long checkSatAssuming(long pointer, long assumptionPointer);
+
+  /**
+   * Check satisfiability assuming the given formulas.
+   * SMT-LIB:
+   * {@code
+   *   ( check-sat-assuming ( <prop_literal>+ ) )
+   * }
+   * @param assumptions the formulas to assume
+   * @return the result of the satisfiability check.
+   */
+  public Result checkSatAssuming(Term[] assumptions)
+  {
+    long[] pointers = Utils.getPointers(assumptions);
+    long resultPointer = checkSatAssuming(pointer, pointers);
+    return new Result(this, resultPointer);
+  }
+
+  private native long checkSatAssuming(long pointer, long[] assumptionPointers);
+
+  /**
+   * Check entailment of the given formula w.r.t. the current set of assertions.
+   * @param term the formula to check entailment for
+   * @return the result of the entailment check.
+   */
+  public Result checkEntailed(Term term)
+  {
+    long resultPointer = checkEntailed(pointer, term.getPointer());
+    return new Result(this, resultPointer);
+  }
+
+  private native long checkEntailed(long pointer, long termPointer);
+
+  /**
+   * Check entailment of the given set of given formulas w.r.t. the current
+   * set of assertions.
+   * @param terms the terms to check entailment for
+   * @return the result of the entailmentcheck.
+   */
+  public Result checkEntailed(Term[] terms)
+  {
+    long[] pointers = Utils.getPointers(terms);
+    long resultPointer = checkEntailed(pointer, pointers);
+    return new Result(this, resultPointer);
+  }
+
+  private native long checkEntailed(long pointer, long[] termPointers);
+
+  /**
+   * Create datatype sort.
+   * SMT-LIB:
+   * {@code
+   *   ( declare-datatype <symbol> <datatype_decl> )
+   * }
+   * @param symbol the name of the datatype sort
+   * @param ctors the constructor declarations of the datatype sort
+   * @return the datatype sort
+   */
+  public Sort declareDatatype(String symbol, DatatypeConstructorDecl[] ctors)
+  {
+    long[] pointers = Utils.getPointers(ctors);
+    long sortPointer = declareDatatype(pointer, symbol, pointers);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long declareDatatype(long pointer, String symbol, long[] declPointers);
+
+  /**
+   * Declare n-ary function symbol.
+   * SMT-LIB:
+   * {@code
+   *   ( declare-fun <symbol> ( <sort>* ) <sort> )
+   * }
+   * @param symbol the name of the function
+   * @param sorts the sorts of the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @return the function
+   */
+  public Term declareFun(String symbol, Sort[] sorts, Sort sort)
+  {
+    long[] sortPointers = Utils.getPointers(sorts);
+    long termPointer = declareFun(pointer, symbol, sortPointers, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long declareFun(
+      long pointer, String symbol, long[] sortPointers, long sortPointer);
+
+  /**
+   * Declare uninterpreted sort.
+   * SMT-LIB:
+   * {@code
+   *   ( declare-sort <symbol> <numeral> )
+   * }
+   * @param symbol the name of the sort
+   * @param arity the arity of the sort
+   * @return the sort
+   */
+  public Sort declareSort(String symbol, int arity) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(arity, "arity");
+    long sortPointer = declareSort(pointer, symbol, arity);
+    return new Sort(this, sortPointer);
+  }
+
+  private native long declareSort(long pointer, String symbol, int arity);
+
+  /**
+   * Define n-ary function in the current context.
+   * SMT-LIB:
+   * {@code
+   *   ( define-fun <function_def> )
+   * }
+   * @param symbol the name of the function
+   * @param boundVars the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @param term the function body
+   * @return the function
+   */
+  public Term defineFun(String symbol, Term[] boundVars, Sort sort, Term term)
+  {
+    return defineFun(symbol, boundVars, sort, term, false);
+  }
+
+  /**
+   * Define n-ary function.
+   * SMT-LIB:
+   * {@code
+   *   ( define-fun <function_def> )
+   * }
+   * @param symbol the name of the function
+   * @param boundVars the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @param term the function body
+   * @param global determines whether this definition is global (i.e. persists
+   *               when popping the context)
+   * @return the function
+   */
+  public Term defineFun(String symbol, Term[] boundVars, Sort sort, Term term, boolean global)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer =
+        defineFun(pointer, symbol, boundVarPointers, sort.getPointer(), term.getPointer(), global);
+    return new Term(this, termPointer);
+  }
+
+  private native long defineFun(long pointer,
+      String symbol,
+      long[] boundVarPointers,
+      long sortPointer,
+      long termPointer,
+      boolean global);
+
+  /**
+   * Define n-ary function in the current context.
+   * SMT-LIB:
+   * {@code
+   * ( define-fun <function_def> )
+   * }
+   * Create parameter 'fun' with mkConst().
+   * @param fun the sorted function
+   * @param boundVars the parameters to this function
+   * @param term the function body
+   * @return the function
+   */
+  public Term defineFun(Term fun, Term[] boundVars, Term term)
+  {
+    return defineFun(fun, boundVars, term, false);
+  }
+  /**
+   * Define n-ary function.
+   * SMT-LIB:
+   * {@code
+   * ( define-fun <function_def> )
+   * }
+   * Create parameter 'fun' with mkConst().
+   * @param fun the sorted function
+   * @param boundVars the parameters to this function
+   * @param term the function body
+   * @param global determines whether this definition is global (i.e. persists
+   *               when popping the context)
+   * @return the function
+   */
+  public Term defineFun(Term fun, Term[] boundVars, Term term, boolean global)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer =
+        defineFun(pointer, fun.getPointer(), boundVarPointers, term.getPointer(), global);
+    return new Term(this, termPointer);
+  }
+
+  private native long defineFun(
+      long pointer, long funPointer, long[] boundVarPointers, long termPointer, boolean global);
+
+  /**
+   * Define recursive function in the current context.
+   * SMT-LIB:
+   * {@code
+   * ( define-fun-rec <function_def> )
+   * }
+   * @param symbol the name of the function
+   * @param boundVars the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @param term the function body
+   * @return the function
+   */
+  public Term defineFunRec(String symbol, Term[] boundVars, Sort sort, Term term)
+  {
+    return defineFunRec(symbol, boundVars, sort, term, false);
+  }
+
+  /**
+   * Define recursive function.
+   * SMT-LIB:
+   * {@code
+   * ( define-fun-rec <function_def> )
+   * }
+   * @param symbol the name of the function
+   * @param boundVars the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @param term the function body
+   * @param global determines whether this definition is global (i.e. persists
+   *               when popping the context)
+   * @return the function
+   */
+  public Term defineFunRec(String symbol, Term[] boundVars, Sort sort, Term term, boolean global)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer = defineFunRec(
+        pointer, symbol, boundVarPointers, sort.getPointer(), term.getPointer(), global);
+    return new Term(this, termPointer);
+  }
+
+  private native long defineFunRec(long pointer,
+      String symbol,
+      long[] boundVarPointers,
+      long sortPointer,
+      long termPointer,
+      boolean global);
+
+  /**
+   * Define recursive function in the current context.
+   * SMT-LIB:
+   * {@code
+   * ( define-fun-rec <function_def> )
+   * }
+   * Create parameter 'fun' with mkConst().
+   * @param fun the sorted function
+   * @param boundVars the parameters to this function
+   * @param term the function body
+   * @return the function
+   */
+
+  public Term defineFunRec(Term fun, Term[] boundVars, Term term)
+  {
+    return defineFunRec(fun, boundVars, term, false);
+  }
+
+  /**
+   * Define recursive function.
+   * SMT-LIB:
+   * {@code
+   * ( define-fun-rec <function_def> )
+   * }
+   * Create parameter 'fun' with mkConst().
+   * @param fun the sorted function
+   * @param boundVars the parameters to this function
+   * @param term the function body
+   * @param global determines whether this definition is global (i.e. persists
+   *               when popping the context)
+   * @return the function
+   */
+  public Term defineFunRec(Term fun, Term[] boundVars, Term term, boolean global)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer =
+        defineFunRec(pointer, fun.getPointer(), boundVarPointers, term.getPointer(), global);
+    return new Term(this, termPointer);
+  }
+
+  private native long defineFunRec(
+      long pointer, long funPointer, long[] boundVarPointers, long termPointer, boolean global);
+
+  /**
+   * Define recursive functions in the current context.
+   * SMT-LIB:
+   * {@code
+   *   ( define-funs-rec ( <function_decl>^{n+1} ) ( <term>^{n+1} ) )
+   * }
+   * Create elements of parameter 'funs' with mkConst().
+   * @param funs the sorted functions
+   * @param boundVars the list of parameters to the functions
+   * @param terms the list of function bodies of the functions
+   */
+  public void defineFunsRec(Term[] funs, Term[][] boundVars, Term[] terms)
+  {
+    defineFunsRec(funs, boundVars, terms, false);
+  }
+  /**
+   * Define recursive functions.
+   * SMT-LIB:
+   * {@code
+   *   ( define-funs-rec ( <function_decl>^{n+1} ) ( <term>^{n+1} ) )
+   * }
+   * Create elements of parameter 'funs' with mkConst().
+   * @param funs the sorted functions
+   * @param boundVars the list of parameters to the functions
+   * @param terms the list of function bodies of the functions
+   * @param global determines whether this definition is global (i.e. persists
+   *               when popping the context)
+   */
+  public void defineFunsRec(Term[] funs, Term[][] boundVars, Term[] terms, boolean global)
+  {
+    long[] funPointers = Utils.getPointers(funs);
+    long[][] boundVarPointers = Utils.getPointers(boundVars);
+    long[] termPointers = Utils.getPointers(terms);
+    defineFunsRec(pointer, funPointers, boundVarPointers, termPointers, global);
+  }
+
+  private native void defineFunsRec(long pointer,
+      long[] funPointers,
+      long[][] boundVarPointers,
+      long[] termPointers,
+      boolean global);
+
+  /**
+   * Echo a given string to the given output stream.
+   * SMT-LIB:
+   * {@code
+   * ( echo <std::string> )
+   * }
+   * @param out the output stream
+   * @param str the string to echo
+   */
+  // TODO: void echo(std::ostream& out, String  str)
+
+  /**
+   * Get the list of asserted formulas.
+   * SMT-LIB:
+   * {@code
+   * ( get-assertions )
+   * }
+   * @return the list of asserted formulas
+   */
+  public Term[] getAssertions()
+  {
+    long[] retPointers = getAssertions(pointer);
+    return Utils.getTerms(this, retPointers);
+  }
+
+  private native long[] getAssertions(long pointer);
+
+  /**
+   * Get info from the solver.
+   * SMT-LIB: {@code ( get-info <info_flag> ) }
+   * @return the info
+   */
+  public String getInfo(String flag)
+  {
+    return getInfo(pointer, flag);
+  }
+
+  private native String getInfo(long pointer, String flag);
+
+  /**
+   * Get the value of a given option.
+   * SMT-LIB:
+   * {@code
+   * ( get-option <keyword> )
+   * }
+   * @param option the option for which the value is queried
+   * @return a string representation of the option value
+   */
+  public String getOption(String option)
+  {
+    return getOption(pointer, option);
+  }
+
+  private native String getOption(long pointer, String option);
+
+  /**
+   * Get all option names that can be used with `setOption`, `getOption` and
+   * `getOptionInfo`.
+   * @return all option names
+   */
+  public String[] getOptionNames()
+  {
+    return getOptionNames(pointer);
+  }
+
+  private native String[] getOptionNames(long pointer);
+
+  /**
+   * Get some information about the given option. Check the `OptionInfo` class
+   * for more details on which information is available.
+   * @return information about the given option
+   */
+  public OptionInfo getOptionInfo(String option)
+  {
+    long optionPointer = getOptionInfo(pointer, option);
+    return new OptionInfo(this, optionPointer);
+  }
+
+  private native long getOptionInfo(long pointer, String option);
+
+  /**
+   * Get the set of unsat ("failed") assumptions.
+   * SMT-LIB:
+   * {@code
+   * ( get-unsat-assumptions )
+   * }
+   * Requires to enable option 'produce-unsat-assumptions'.
+   * @return the set of unsat assumptions.
+   */
+  public Term[] getUnsatAssumptions()
+  {
+    long[] retPointers = getUnsatAssumptions(pointer);
+    return Utils.getTerms(this, retPointers);
+  }
+
+  private native long[] getUnsatAssumptions(long pointer);
+
+  /**
+   * Get the unsatisfiable core.
+   * SMT-LIB:
+   * {@code
+   * ( get-unsat-core )
+   * }
+   * Requires to enable option 'produce-unsat-cores'.
+   * @return a set of terms representing the unsatisfiable core
+   */
+  public Term[] getUnsatCore()
+  {
+    long[] retPointers = getUnsatCore(pointer);
+    return Utils.getTerms(this, retPointers);
+  }
+
+  private native long[] getUnsatCore(long pointer);
+
+  /**
+   * Get a difficulty estimate for an asserted formula. This method is
+   * intended to be called immediately after any response to a checkSat.
+   *
+   * @return a map from (a subset of) the input assertions to a real value that
+   * is an estimate of how difficult each assertion was to solve. Unmentioned
+   * assertions can be assumed to have zero difficulty.
+   */
+  public Map<Term, Term> getDifficulty()
+  {
+    Map<Long, Long> map = getDifficulty(pointer);
+    Map<Term, Term> ret = new HashMap<>();
+    for (Map.Entry<Long, Long> entry : map.entrySet())
+    {
+      Term key = new Term(this, entry.getKey());
+      Term value = new Term(this, entry.getValue());
+      ret.put(key, value);
+    }
+    return ret;
+  }
+
+  private native Map<Long, Long> getDifficulty(long pointer);
+
+  /**
+   * Get the refutation proof
+   * SMT-LIB:
+   * {@code
+   * ( get-proof )
+   * }
+   * Requires to enable option 'produce-proofs'.
+   * @return a string representing the proof, according to the value of
+   * proof-format-mode.
+   */
+  public String getProof()
+  {
+    return getProof(pointer);
+  }
+
+  private native String getProof(long pointer);
+
+  /**
+   * Get the value of the given term in the current model.
+   * SMT-LIB:
+   * {@code
+   * ( get-value ( <term> ) )
+   * }
+   * @param term the term for which the value is queried
+   * @return the value of the given term
+   */
+  public Term getValue(Term term)
+  {
+    long termPointer = getValue(pointer, term.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long getValue(long pointer, long termPointer);
+
+  /**
+   * Get the values of the given terms in the current model.
+   * SMT-LIB:
+   * {@code
+   * ( get-value ( <term>+ ) )
+   * }
+   * @param terms the terms for which the value is queried
+   * @return the values of the given terms
+   */
+  public Term[] getValue(Term[] terms)
+  {
+    long[] pointers = Utils.getPointers(terms);
+    long[] retPointers = getValue(pointer, pointers);
+    return Utils.getTerms(this, retPointers);
+  }
+
+  private native long[] getValue(long pointer, long[] termPointers);
+
+  /**
+   * Get the domain elements of uninterpreted sort s in the current model. The
+   * current model interprets s as the finite sort whose domain elements are
+   * given in the return value of this method.
+   *
+   * @param s The uninterpreted sort in question
+   * @return the domain elements of s in the current model
+   */
+  public Term[] getModelDomainElements(Sort s)
+  {
+    long[] pointers = getModelDomainElements(pointer, s.getPointer());
+    return Utils.getTerms(this, pointers);
+  }
+
+  private native long[] getModelDomainElements(long pointer, long sortPointer);
+
+  /**
+   * This returns false if the model value of free constant v was not essential
+   * for showing the satisfiability of the last call to checkSat using the
+   * current model. This method will only return false (for any v) if
+   * the model-cores option has been set.
+   *
+   * @param v The term in question
+   * @return true if v is a model core symbol
+   */
+  public boolean isModelCoreSymbol(Term v)
+  {
+    return isModelCoreSymbol(pointer, v.getPointer());
+  }
+
+  private native boolean isModelCoreSymbol(long pointer, long termPointer);
+
+  /**
+   * Get the model
+   * SMT-LIB:
+   * {@code
+   * ( get-model )
+   * }
+   * Requires to enable option 'produce-models'.
+   * @param sorts The list of uninterpreted sorts that should be printed in the
+   * model.
+   * @param vars The list of free constants that should be printed in the
+   * model. A subset of these may be printed based on isModelCoreSymbol.
+   * @return a string representing the model.
+   */
+  public String getModel(Sort[] sorts, Term[] vars)
+  {
+    long[] sortPointers = Utils.getPointers(sorts);
+    long[] varPointers = Utils.getPointers(vars);
+    return getModel(pointer, sortPointers, varPointers);
+  }
+
+  private native String getModel(long pointer, long[] sortPointers, long[] varPointers);
+
+  /**
+   * Do quantifier elimination.
+   * SMT-LIB:
+   * {@code
+   * ( get-qe <q> )
+   * }
+   * Requires a logic that supports quantifier elimination. Currently, the only
+   * logics supported by quantifier elimination is LRA and LIA.
+   * @param q a quantified formula of the form:
+   *   Q x1...xn. P( x1...xn, y1...yn )
+   * where P( x1...xn, y1...yn ) is a quantifier-free formula
+   * @return a formula ret such that, given the current set of formulas A
+   * asserted to this solver:
+   *   - ( A ^ q ) and ( A ^ ret ) are equivalent
+   *   - ret is quantifier-free formula containing only free variables in
+   *     y1...yn.
+   */
+  public Term getQuantifierElimination(Term q)
+  {
+    long termPointer = getQuantifierElimination(pointer, q.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long getQuantifierElimination(long pointer, long qPointer);
+
+  /**
+   * Do partial quantifier elimination, which can be used for incrementally
+   * computing the result of a quantifier elimination.
+   * SMT-LIB:
+   * {@code
+   * ( get-qe-disjunct <q> )
+   * }
+   * Requires a logic that supports quantifier elimination. Currently, the only
+   * logics supported by quantifier elimination is LRA and LIA.
+   * @param q a quantified formula of the form:
+   *   Q x1...xn. P( x1...xn, y1...yn )
+   * where P( x1...xn, y1...yn ) is a quantifier-free formula
+   * @return a formula ret such that, given the current set of formulas A
+   * asserted to this solver:
+   *   - {@code (A ^ q) => (A ^ ret)} if Q is forall or {@code (A ^ ret) => (A ^ q)} if Q is
+   *     exists,
+   *   - ret is quantifier-free formula containing only free variables in
+   *     y1...yn,
+   *   - If Q is exists, let A^Q_n be the formula
+   *       {@code A ^ ~ret^Q_1 ^ ... ^ ~ret^Q_n}
+   *     where for each i=1,...n, formula ret^Q_i is the result of calling
+   *     getQuantifierEliminationDisjunct for q with the set of assertions
+   *     {@code A^Q_{i-1}}. Similarly, if Q is forall, then let {@code A^Q_n} be
+   *       {@code A ^ ret^Q_1 ^ ... ^ ret^Q_n }
+   *     where ret^Q_i is the same as above. In either case, we have
+   *     that ret^Q_j will eventually be true or false, for some finite j.
+   */
+  public Term getQuantifierEliminationDisjunct(Term q)
+  {
+    long termPointer = getQuantifierEliminationDisjunct(pointer, q.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long getQuantifierEliminationDisjunct(long pointer, long qPointer);
+
+  /**
+   * When using separation logic, this sets the location sort and the
+   * datatype sort to the given ones. This method should be invoked exactly
+   * once, before any separation logic constraints are provided.
+   * @param locSort The location sort of the heap
+   * @param dataSort The data sort of the heap
+   */
+  public void declareSeparationHeap(Sort locSort, Sort dataSort)
+  {
+    declareSeparationHeap(pointer, locSort.getPointer(), dataSort.getPointer());
+  }
+
+  private native void declareSeparationHeap(
+      long pointer, long locSortPointer, long dataSortPointer);
+
+  /**
+   * When using separation logic, obtain the term for the heap.
+   * @return The term for the heap
+   */
+  public Term getSeparationHeap()
+  {
+    long termPointer = getSeparationHeap(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long getSeparationHeap(long pointer);
+
+  /**
+   * When using separation logic, obtain the term for nil.
+   * @return The term for nil
+   */
+  public Term getSeparationNilTerm()
+  {
+    long termPointer = getSeparationNilTerm(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long getSeparationNilTerm(long pointer);
+
+  /**
+   * Declare a symbolic pool of terms with the given initial value.
+   * SMT-LIB:
+   * {@code
+   * ( declare-pool <symbol> <sort> ( <term>* ) )
+   * }
+   * @param symbol The name of the pool
+   * @param sort The sort of the elements of the pool.
+   * @param initValue The initial value of the pool
+   */
+  public Term declarePool(String symbol, Sort sort, Term[] initValue)
+  {
+    long[] termPointers = Utils.getPointers(initValue);
+    long termPointer = declarePool(pointer, symbol, sort.getPointer(), termPointers);
+    return new Term(this, termPointer);
+  }
+
+  private native long declarePool(
+      long pointer, String symbol, long sortPointer, long[] termPointers);
+
+  /**
+   * Pop a level from the assertion stack.
+   * SMT-LIB:
+   * {@code
+   * ( pop <numeral> )
+   * }
+   */
+  public void pop() throws CVC5ApiException
+  {
+    pop(1);
+  }
+
+  /**
+   * Pop (a) level(s) from the assertion stack.
+   * SMT-LIB:
+   * {@code
+   * ( pop <numeral> )
+   * }
+   * @param nscopes the number of levels to pop
+   */
+  public void pop(int nscopes) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(nscopes, "nscopes");
+    pop(pointer, nscopes);
+  }
+
+  private native void pop(long pointer, int nscopes);
+
+  /**
+   * Get an interpolant
+   * SMT-LIB:
+   * {@code
+   * ( get-interpol <conj> )
+   * }
+   * Requires to enable option 'produce-interpols'.
+   * @param conj the conjecture term
+   * @param output a Term I such that {@code A->I} and {@code I->B} are valid, where A is the
+   *        current set of assertions and B is given in the input by conj.
+   * @return true if it gets I successfully, false otherwise.
+   */
+  public boolean getInterpolant(Term conj, Term output)
+  {
+    return getInterpolant(pointer, conj.getPointer(), output.getPointer());
+  }
+
+  private native boolean getInterpolant(long pointer, long conjPointer, long outputPointer);
+
+  /**
+   * Get an interpolant
+   * SMT-LIB:
+   * {@code
+   * ( get-interpol <conj> <g> )
+   * }
+   * Requires to enable option 'produce-interpols'.
+   * @param conj the conjecture term
+   * @param grammar the grammar for the interpolant I
+   * @param output a Term I such that {@code A->I} and {@code I->B} are valid, where A is the
+   *        current set of assertions and B is given in the input by conj.
+   * @return true if it gets I successfully, false otherwise.
+   */
+  public boolean getInterpolant(Term conj, Grammar grammar, Term output)
+  {
+    return getInterpolant(pointer, conj.getPointer(), grammar.getPointer(), output.getPointer());
+  }
+
+  private native boolean getInterpolant(
+      long pointer, long conjPointer, long grammarPointer, long outputPointer);
+
+  /**
+   * Get an abduct.
+   * SMT-LIB:
+   * {@code
+   * ( get-abduct <conj> )
+   * }
+   * Requires enabling option 'produce-abducts'
+   * @param conj the conjecture term
+   * @param output a term C such that A^C is satisfiable, and A^~B^C is
+   *        unsatisfiable, where A is the current set of assertions and B is
+   *        given in the input by conj
+   * @return true if it gets C successfully, false otherwise
+   */
+  public boolean getAbduct(Term conj, Term output)
+  {
+    return getAbduct(pointer, conj.getPointer(), output.getPointer());
+  }
+
+  private native boolean getAbduct(long pointer, long conjPointer, long outputPointer);
+  /**
+   * Get an abduct.
+   * SMT-LIB:
+   * {@code
+   * ( get-abduct <conj> <g> )
+   * }
+   * Requires enabling option 'produce-abducts'
+   * @param conj the conjecture term
+   * @param grammar the grammar for the abduct C
+   * @param output a term C such that A^C is satisfiable, and A^~B^C is
+   *        unsatisfiable, where A is the current set of assertions and B is
+   *        given in the input by conj
+   * @return true if it gets C successfully, false otherwise
+   */
+  public boolean getAbduct(Term conj, Grammar grammar, Term output)
+  {
+    return getAbduct(pointer, conj.getPointer(), grammar.getPointer(), output.getPointer());
+  }
+
+  private native boolean getAbduct(
+      long pointer, long conjPointer, long grammarPointer, long outputPointer);
+
+  /**
+   * Block the current model. Can be called only if immediately preceded by a
+   * SAT or INVALID query.
+   * SMT-LIB:
+   * {@code
+   * ( block-model )
+   * }
+   * Requires enabling 'produce-models' option and setting 'block-models' option
+   * to a mode other than "none".
+   */
+  public void blockModel()
+  {
+    blockModel(pointer);
+  }
+
+  private native void blockModel(long pointer);
+
+  /**
+   * Block the current model values of (at least) the values in terms. Can be
+   * called only if immediately preceded by a SAT or NOT_ENTAILED query.
+   * SMT-LIB:
+   * {@code
+   * ( block-model-values ( <terms>+ ) )
+   * }
+   * Requires enabling 'produce-models' option and setting 'block-models' option
+   * to a mode other than "none".
+   */
+  public void blockModelValues(Term[] terms)
+  {
+    long[] pointers = Utils.getPointers(terms);
+    blockModelValues(pointer, pointers);
+  }
+
+  private native void blockModelValues(long pointer, long[] termPointers);
+
+  /**
+   * Print all instantiations made by the quantifiers module.
+   * @param out the output stream
+   */
+  // TODO: void printInstantiations(std::ostream& out)
+
+  /**
+   * Push a level to the assertion stack.
+   * SMT-LIB:
+   * {@code
+   * ( push <numeral> )
+   * }
+   */
+  public void push() throws CVC5ApiException
+  {
+    push(1);
+  }
+
+  /**
+   * Push (a) level(s) to the assertion stack.
+   * SMT-LIB:
+   * {@code
+   * ( push <numeral> )
+   * }
+   * @param nscopes the number of levels to push
+   */
+  public void push(int nscopes) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(nscopes, "nscopes");
+    push(pointer, nscopes);
+  }
+
+  private native void push(long pointer, int nscopes);
+
+  /**
+   * Remove all assertions.
+   * SMT-LIB:
+   * {@code
+   * ( reset-assertions )
+   * }
+   */
+  public void resetAssertions()
+  {
+    resetAssertions(pointer);
+  }
+
+  private native void resetAssertions(long pointer);
+
+  /**
+   * Set info.
+   * SMT-LIB:
+   * {@code
+   * ( set-info <attribute> )
+   * }
+   * @param keyword the info flag
+   * @param value the value of the info flag
+   */
+  public void setInfo(String keyword, String value) throws CVC5ApiException
+  {
+    setInfo(pointer, keyword, value);
+  }
+
+  private native void setInfo(long pointer, String keyword, String value) throws CVC5ApiException;
+
+  /**
+   * Set logic.
+   * SMT-LIB:
+   * {@code
+   * ( set-logic <symbol> )
+   * }
+   * @param logic the logic to set
+   */
+  public void setLogic(String logic) throws CVC5ApiException
+  {
+    setLogic(pointer, logic);
+  }
+
+  private native void setLogic(long pointer, String logic) throws CVC5ApiException;
+
+  /**
+   * Set option.
+   * SMT-LIB:
+   * {@code
+   *   ( set-option <option> )
+   * }
+   * @param option the option name
+   * @param value the option value
+   */
+  public void setOption(String option, String value)
+  {
+    setOption(pointer, option, value);
+  }
+
+  private native void setOption(long pointer, String option, String value);
+
+  /**
+   * If needed, convert this term to a given sort. Note that the sort of the
+   * term must be convertible into the target sort. Currently only Int to Real
+   * conversions are supported.
+   * @param t the term
+   * @param s the target sort
+   * @return the term wrapped into a sort conversion if needed
+   */
+  public Term ensureTermSort(Term t, Sort s)
+  {
+    long termPointer = ensureTermSort(pointer, t.getPointer(), s.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long ensureTermSort(long pointer, long termPointer, long sortPointer);
+
+  /**
+   * Append \p symbol to the current list of universal variables.
+   * @param sort the sort of the universal variable
+   * @return the universal variable
+   */
+  public Term mkSygusVar(Sort sort)
+  {
+    return mkSygusVar(sort, "");
+  }
+  /**
+   * Append \p symbol to the current list of universal variables.
+   * SyGuS v2:
+   * {@code
+   *   ( declare-var <symbol> <sort> )
+   * }
+   * @param sort the sort of the universal variable
+   * @param symbol the name of the universal variable
+   * @return the universal variable
+   */
+  public Term mkSygusVar(Sort sort, String symbol)
+  {
+    long termPointer = mkSygusVar(pointer, sort.getPointer(), symbol);
+    return new Term(this, termPointer);
+  }
+
+  private native long mkSygusVar(long pointer, long sortPointer, String symbol);
+
+  /**
+   * Create a Sygus grammar. The first non-terminal is treated as the starting
+   * non-terminal, so the order of non-terminals matters.
+   *
+   * @param boundVars the parameters to corresponding synth-fun/synth-inv
+   * @param ntSymbols the pre-declaration of the non-terminal symbols
+   * @return the grammar
+   */
+  public Grammar mkSygusGrammar(Term[] boundVars, Term[] ntSymbols)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long[] ntSymbolPointers = Utils.getPointers(ntSymbols);
+    long grammarPointer = mkSygusGrammar(pointer, boundVarPointers, ntSymbolPointers);
+    return new Grammar(this, grammarPointer);
+  }
+
+  private native long mkSygusGrammar(
+      long pointer, long[] boundVarPointers, long[] ntSymbolPointers);
+
+  /**
+   * Synthesize n-ary function.
+   * SyGuS v2:
+   * {@code
+   *   ( synth-fun <symbol> ( <boundVars>* ) <sort> )
+   * }
+   * @param symbol the name of the function
+   * @param boundVars the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @return the function
+   */
+  public Term synthFun(String symbol, Term[] boundVars, Sort sort)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer = synthFun(pointer, symbol, boundVarPointers, sort.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long synthFun(
+      long pointer, String symbol, long[] boundVarPointers, long sortPointer);
+
+  /**
+   * Synthesize n-ary function following specified syntactic constraints.
+   * SyGuS v2:
+   * {@code
+   *   ( synth-fun <symbol> ( <boundVars>* ) <sort> <g> )
+   * }
+   * @param symbol the name of the function
+   * @param boundVars the parameters to this function
+   * @param sort the sort of the return value of this function
+   * @param grammar the syntactic constraints
+   * @return the function
+   */
+  public Term synthFun(String symbol, Term[] boundVars, Sort sort, Grammar grammar)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer =
+        synthFun(pointer, symbol, boundVarPointers, sort.getPointer(), grammar.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long synthFun(
+      long pointer, String symbol, long[] boundVarPointers, long sortPointer, long grammarPointer);
+
+  /**
+   * Synthesize invariant.
+   * SyGuS v2:
+   * {@code
+   *   ( synth-inv <symbol> ( <boundVars>* ) )
+   * }
+   * @param symbol the name of the invariant
+   * @param boundVars the parameters to this invariant
+   * @return the invariant
+   */
+  public Term synthInv(String symbol, Term[] boundVars)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer = synthInv(pointer, symbol, boundVarPointers);
+    return new Term(this, termPointer);
+  }
+
+  private native long synthInv(long pointer, String symbol, long[] boundVarPointers);
+
+  /**
+   * Synthesize invariant following specified syntactic constraints.
+   * SyGuS v2:
+   * {@code
+   *   ( synth-inv <symbol> ( <boundVars>* ) <g> )
+   * }
+   * @param symbol the name of the invariant
+   * @param boundVars the parameters to this invariant
+   * @param grammar the syntactic constraints
+   * @return the invariant
+   */
+  public Term synthInv(String symbol, Term[] boundVars, Grammar grammar)
+  {
+    long[] boundVarPointers = Utils.getPointers(boundVars);
+    long termPointer = synthInv(pointer, symbol, boundVarPointers, grammar.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long synthInv(
+      long pointer, String symbol, long[] boundVarPointers, long grammarPointer);
+
+  /**
+   * Add a forumla to the set of Sygus constraints.
+   * SyGuS v2:
+   * {@code
+   *   ( constraint <term> )
+   * }
+   * @param term the formula to add as a constraint
+   */
+  public void addSygusConstraint(Term term)
+  {
+    addSygusConstraint(pointer, term.getPointer());
+  }
+
+  private native void addSygusConstraint(long pointer, long termPointer);
+
+  /**
+   * Add a forumla to the set of Sygus assumptions.
+   * SyGuS v2:
+   * {@code
+   *   ( assume <term> )
+   * }
+   * @param term the formula to add as an assumption
+   */
+  public void addSygusAssume(Term term)
+  {
+    addSygusAssume(pointer, term.getPointer());
+  }
+
+  private native void addSygusAssume(long pointer, long termPointer);
+
+  /**
+   * Add a set of Sygus constraints to the current state that correspond to an
+   * invariant synthesis problem.
+   * SyGuS v2:
+   * {@code
+   *   ( inv-constraint <inv> <pre> <trans> <post> )
+   * }
+   * @param inv the function-to-synthesize
+   * @param pre the pre-condition
+   * @param trans the transition relation
+   * @param post the post-condition
+   */
+  public void addSygusInvConstraint(Term inv, Term pre, Term trans, Term post)
+  {
+    addSygusInvConstraint(
+        pointer, inv.getPointer(), pre.getPointer(), trans.getPointer(), post.getPointer());
+  }
+
+  private native void addSygusInvConstraint(
+      long pointer, long invPointer, long prePointer, long transPointer, long postPointer);
+
+  /**
+   * Try to find a solution for the synthesis conjecture corresponding to the
+   * current list of functions-to-synthesize, universal variables and
+   * constraints.
+   * SyGuS v2:
+   * {@code
+   *   ( check-synth )
+   * }
+   * @return the result of the synthesis conjecture.
+   */
+  public Result checkSynth()
+  {
+    long resultPointer = checkSynth(pointer);
+    return new Result(this, resultPointer);
+  }
+
+  private native long checkSynth(long pointer);
+
+  /**
+   * Get the synthesis solution of the given term. This method should be called
+   * immediately after the solver answers unsat for sygus input.
+   * @param term the term for which the synthesis solution is queried
+   * @return the synthesis solution of the given term
+   */
+  public Term getSynthSolution(Term term)
+  {
+    long termPointer = getSynthSolution(pointer, term.getPointer());
+    return new Term(this, termPointer);
+  }
+
+  private native long getSynthSolution(long pointer, long termPointer);
+
+  /**
+   * Get the synthesis solutions of the given terms. This method should be
+   * called immediately after the solver answers unsat for sygus input.
+   * @param terms the terms for which the synthesis solutions is queried
+   * @return the synthesis solutions of the given terms
+   */
+  public Term[] getSynthSolutions(Term[] terms)
+  {
+    long[] termPointers = Utils.getPointers(terms);
+    long[] retPointers = getSynthSolutions(pointer, termPointers);
+    return Utils.getTerms(this, retPointers);
+  }
+
+  private native long[] getSynthSolutions(long pointer, long[] termPointers);
+
+  /**
+   * Returns a snapshot of the current state of the statistic values of this
+   * solver. The returned object is completely decoupled from the solver and
+   * will not change when the solver is used again.
+   */
+  public Statistics getStatistics()
+  {
+    long statisticsPointer = getStatistics(pointer);
+    return new Statistics(this, statisticsPointer);
+  }
+
+  private native long getStatistics(long pointer);
+
+  /**
+   * @return null term
+   */
+  public Term getNullTerm()
+  {
+    long termPointer = getNullTerm(pointer);
+    return new Term(this, termPointer);
+  }
+
+  private native long getNullTerm(long pointer);
+
+  /**
+   * @return null result
+   */
+  public Result getNullResult()
+  {
+    long resultPointer = getNullResult(pointer);
+    return new Result(this, resultPointer);
+  }
+
+  private native long getNullResult(long pointer);
+
+  /**
+   * @return null op
+   */
+  public Op getNullOp()
+  {
+    long opPointer = getNullOp(pointer);
+    return new Op(this, opPointer);
+  }
+
+  private native long getNullOp(long pointer);
+
+  /**
+   * @return null op
+   */
+  public DatatypeDecl getNullDatatypeDecl()
+  {
+    long declPointer = getNullDatatypeDecl(pointer);
+    return new DatatypeDecl(this, declPointer);
+  }
+
+  private native long getNullDatatypeDecl(long pointer);
+}
diff --git a/src/api/java/io/github/cvc5/api/Sort.java b/src/api/java/io/github/cvc5/api/Sort.java
new file mode 100644 (file)
index 0000000..ec7091e
--- /dev/null
@@ -0,0 +1,802 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.util.List;
+
+public class Sort extends AbstractPointer implements Comparable<Sort>
+{
+  // region construction and destruction
+  Sort(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * Comparison for structural equality.
+   * @param s the sort to compare to
+   * @return true if the sorts are equal
+   */
+  @Override public boolean equals(Object s)
+  {
+    if (this == s)
+      return true;
+    if (s == null || getClass() != s.getClass())
+      return false;
+    Sort sort = (Sort) s;
+    if (this.pointer == sort.pointer)
+    {
+      return true;
+    }
+    return equals(pointer, sort.getPointer());
+  }
+
+  private native boolean equals(long pointer1, long pointer2);
+
+  /**
+   * Comparison for ordering on sorts.
+   *
+   * @param s the sort to compare to
+   * @return a negative integer, zero, or a positive integer as this sort
+   * is less than, equal to, or greater than the specified sort.
+   */
+  @Override public int compareTo(Sort s)
+  {
+    return this.compareTo(pointer, s.getPointer());
+  }
+
+  private native int compareTo(long pointer1, long pointer2);
+
+  /**
+   * @return true if this Sort is a null sort.
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * Is this a Boolean sort?
+   * @return true if the sort is a Boolean sort
+   */
+  public boolean isBoolean()
+  {
+    return isBoolean(pointer);
+  }
+
+  private native boolean isBoolean(long pointer);
+
+  /**
+   * Is this a integer sort?
+   * @return true if the sort is a integer sort
+   */
+  public boolean isInteger()
+  {
+    return isInteger(pointer);
+  }
+
+  private native boolean isInteger(long pointer);
+
+  /**
+   * Is this a real sort?
+   * @return true if the sort is a real sort
+   */
+  public boolean isReal()
+  {
+    return isReal(pointer);
+  }
+
+  private native boolean isReal(long pointer);
+
+  /**
+   * Is this a string sort?
+   * @return true if the sort is the string sort
+   */
+  public boolean isString()
+  {
+    return isString(pointer);
+  }
+
+  private native boolean isString(long pointer);
+
+  /**
+   * Is this a regexp sort?
+   * @return true if the sort is the regexp sort
+   */
+  public boolean isRegExp()
+  {
+    return isRegExp(pointer);
+  }
+
+  private native boolean isRegExp(long pointer);
+
+  /**
+   * Is this a rounding mode sort?
+   * @return true if the sort is the rounding mode sort
+   */
+  public boolean isRoundingMode()
+  {
+    return isRoundingMode(pointer);
+  }
+
+  private native boolean isRoundingMode(long pointer);
+
+  /**
+   * Is this a bit-vector sort?
+   * @return true if the sort is a bit-vector sort
+   */
+  public boolean isBitVector()
+  {
+    return isBitVector(pointer);
+  }
+
+  private native boolean isBitVector(long pointer);
+
+  /**
+   * Is this a floating-point sort?
+   * @return true if the sort is a floating-point sort
+   */
+  public boolean isFloatingPoint()
+  {
+    return isFloatingPoint(pointer);
+  }
+
+  private native boolean isFloatingPoint(long pointer);
+
+  /**
+   * Is this a datatype sort?
+   * @return true if the sort is a datatype sort
+   */
+  public boolean isDatatype()
+  {
+    return isDatatype(pointer);
+  }
+
+  private native boolean isDatatype(long pointer);
+
+  /**
+   * Is this a parametric datatype sort?
+   * @return true if the sort is a parametric datatype sort
+   */
+  public boolean isParametricDatatype()
+  {
+    return isParametricDatatype(pointer);
+  }
+
+  private native boolean isParametricDatatype(long pointer);
+
+  /**
+   * Is this a constructor sort?
+   * @return true if the sort is a constructor sort
+   */
+  public boolean isConstructor()
+  {
+    return isConstructor(pointer);
+  }
+
+  private native boolean isConstructor(long pointer);
+
+  /**
+   * Is this a selector sort?
+   * @return true if the sort is a selector sort
+   */
+  public boolean isSelector()
+  {
+    return isSelector(pointer);
+  }
+
+  private native boolean isSelector(long pointer);
+
+  /**
+   * Is this a tester sort?
+   * @return true if the sort is a tester sort
+   */
+  public boolean isTester()
+  {
+    return isTester(pointer);
+  }
+
+  private native boolean isTester(long pointer);
+
+  /**
+   * Is this a datatype updater sort?
+   * @return true if the sort is a datatype updater sort
+   */
+  public boolean isUpdater()
+  {
+    return isUpdater(pointer);
+  }
+
+  private native boolean isUpdater(long pointer);
+
+  /**
+   * Is this a function sort?
+   * @return true if the sort is a function sort
+   */
+  public boolean isFunction()
+  {
+    return isFunction(pointer);
+  }
+
+  private native boolean isFunction(long pointer);
+
+  /**
+   * Is this a predicate sort?
+   * That is, is this a function sort mapping to Boolean? All predicate
+   * sorts are also function sorts.
+   * @return true if the sort is a predicate sort
+   */
+  public boolean isPredicate()
+  {
+    return isPredicate(pointer);
+  }
+
+  private native boolean isPredicate(long pointer);
+
+  /**
+   * Is this a tuple sort?
+   * @return true if the sort is a tuple sort
+   */
+  public boolean isTuple()
+  {
+    return isTuple(pointer);
+  }
+
+  private native boolean isTuple(long pointer);
+
+  /**
+   * Is this a record sort?
+   * @return true if the sort is a record sort
+   */
+  public boolean isRecord()
+  {
+    return isRecord(pointer);
+  }
+
+  private native boolean isRecord(long pointer);
+
+  /**
+   * Is this an array sort?
+   * @return true if the sort is a array sort
+   */
+  public boolean isArray()
+  {
+    return isArray(pointer);
+  }
+
+  private native boolean isArray(long pointer);
+
+  /**
+   * Is this a Set sort?
+   * @return true if the sort is a Set sort
+   */
+  public boolean isSet()
+  {
+    return isSet(pointer);
+  }
+
+  private native boolean isSet(long pointer);
+
+  /**
+   * Is this a Bag sort?
+   * @return true if the sort is a Bag sort
+   */
+  public boolean isBag()
+  {
+    return isBag(pointer);
+  }
+
+  private native boolean isBag(long pointer);
+
+  /**
+   * Is this a Sequence sort?
+   * @return true if the sort is a Sequence sort
+   */
+  public boolean isSequence()
+  {
+    return isSequence(pointer);
+  }
+
+  private native boolean isSequence(long pointer);
+
+  /**
+   * Is this a sort kind?
+   * @return true if this is a sort kind
+   */
+  public boolean isUninterpretedSort()
+  {
+    return isUninterpretedSort(pointer);
+  }
+
+  private native boolean isUninterpretedSort(long pointer);
+
+  /**
+   * Is this a sort constructor kind?
+   * @return true if this is a sort constructor kind
+   */
+  public boolean isSortConstructor()
+  {
+    return isSortConstructor(pointer);
+  }
+
+  private native boolean isSortConstructor(long pointer);
+
+  /**
+   * Is this a first-class sort?
+   * First-class sorts are sorts for which:
+   * (1) we handle equalities between terms of that type, and
+   * (2) they are allowed to be parameters of parametric sorts (e.g. index or
+   *     element sorts of arrays).
+   *
+   * Examples of sorts that are not first-class include sort constructor sorts
+   * and regular expression sorts.
+   *
+   * @return true if this is a first-class sort
+   */
+  public boolean isFirstClass()
+  {
+    return isFirstClass(pointer);
+  }
+
+  private native boolean isFirstClass(long pointer);
+
+  /**
+   * Is this a function-LIKE sort?
+   *
+   * Anything function-like except arrays (e.g., datatype selectors) is
+   * considered a function here. Function-like terms can not be the argument
+   * or return value for any term that is function-like.
+   * This is mainly to avoid higher order.
+   *
+   * Note that arrays are explicitly not considered function-like here.
+   *
+   * @return true if this is a function-like sort
+   */
+  public boolean isFunctionLike()
+  {
+    return isFunctionLike(pointer);
+  }
+
+  private native boolean isFunctionLike(long pointer);
+
+  /**
+   * Is this sort a subsort of the given sort?
+   * @return true if this sort is a subsort of s
+   */
+  public boolean isSubsortOf(Sort s)
+  {
+    return isSubsortOf(pointer, s.getPointer());
+  }
+
+  private native boolean isSubsortOf(long pointer, long sortPointer);
+
+  /**
+   * Is this sort comparable to the given sort (i.e., do they share
+   * a common ancestor in the subsort tree)?
+   * @return true if this sort is comparable to s
+   */
+  public boolean isComparableTo(Sort s)
+  {
+    return isComparableTo(pointer, s.getPointer());
+  }
+
+  private native boolean isComparableTo(long pointer, long sortPointer);
+
+  /**
+   * @return the underlying datatype of a datatype sort
+   */
+  public Datatype getDatatype()
+  {
+    long datatypePointer = getDatatype(pointer);
+    return new Datatype(solver, datatypePointer);
+  }
+
+  private native long getDatatype(long pointer);
+
+  /**
+   * Instantiate a parameterized datatype/sort sort.
+   * Create sorts parameter with Solver.mkParamSort().
+   * @param params the list of sort parameters to instantiate with
+   */
+  public Sort instantiate(List<Sort> params)
+  {
+    return instantiate(params.toArray(new Sort[0]));
+  }
+
+  /**
+   * Instantiate a parameterized datatype/sort sort.
+   * Create sorts parameter with Solver.mkParamSort().
+   * @param params the list of sort parameters to instantiate with
+   */
+  public Sort instantiate(Sort[] params)
+  {
+    long[] paramsPointers = Utils.getPointers(params);
+    long sortPointer = instantiate(pointer, paramsPointers);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long instantiate(long pointer, long[] paramsPointers);
+
+  /**
+   * Substitution of Sorts.
+   * @param sort the subsort to be substituted within this sort.
+   * @param replacement the sort replacing the substituted subsort.
+   */
+  public Sort substitute(Sort sort, Sort replacement)
+  {
+    long sortPointer = substitute(pointer, sort.getPointer(), replacement.getPointer());
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long substitute(long pointer, long sortPointer, long replacementPointer);
+
+  /**
+   * Simultaneous substitution of Sorts.
+   * @param sorts the subsorts to be substituted within this sort.
+   * @param replacements the sort replacing the substituted subsorts.
+   */
+  public Sort substitute(Sort[] sorts, Sort[] replacements)
+  {
+    long[] sortPointers = Utils.getPointers(sorts);
+    long[] replacementPointers = Utils.getPointers(sorts);
+    long sortPointer = substitute(pointer, sortPointers, replacementPointers);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long substitute(long pointer, long[] sortPointers, long[] replacementPointers);
+
+  /**
+   * Output a string representation of this sort to a given stream.
+   * @param out the output stream
+   */
+  // TODO: do we need to support this?
+  // void toStream(std::ostream& out)
+
+  /**
+   * @return a string representation of this sort
+   */
+  protected native String toString(long pointer);
+
+  /* Constructor sort ------------------------------------------------------- */
+
+  /**
+   * @return the arity of a constructor sort
+   */
+  public int getConstructorArity()
+  {
+    return getConstructorArity(pointer);
+  }
+
+  private native int getConstructorArity(long pointer);
+
+  /**
+   * @return the domain sorts of a constructor sort
+   */
+  public Sort[] getConstructorDomainSorts()
+  {
+    long[] pointers = getConstructorDomainSorts(pointer);
+    return Utils.getSorts(solver, pointers);
+  }
+
+  private native long[] getConstructorDomainSorts(long pointer);
+
+  /**
+   * @return the codomain sort of a constructor sort
+   */
+  public Sort getConstructorCodomainSort()
+  {
+    long sortPointer = getConstructorCodomainSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getConstructorCodomainSort(long pointer);
+
+  /* Selector sort ------------------------------------------------------- */
+
+  /**
+   * @return the domain sort of a selector sort
+   */
+  public Sort getSelectorDomainSort()
+  {
+    long sortPointer = getSelectorDomainSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getSelectorDomainSort(long pointer);
+
+  /**
+   * @return the codomain sort of a selector sort
+   */
+  public Sort getSelectorCodomainSort()
+  {
+    long sortPointer = getSelectorCodomainSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getSelectorCodomainSort(long pointer);
+
+  /* Tester sort ------------------------------------------------------- */
+
+  /**
+   * @return the domain sort of a tester sort
+   */
+  public Sort getTesterDomainSort()
+  {
+    long sortPointer = getTesterDomainSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getTesterDomainSort(long pointer);
+
+  /**
+   * @return the codomain sort of a tester sort, which is the Boolean sort
+   */
+  public Sort getTesterCodomainSort()
+  {
+    long sortPointer = getTesterCodomainSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getTesterCodomainSort(long pointer);
+
+  /* Function sort ------------------------------------------------------- */
+
+  /**
+   * @return the arity of a function sort
+   */
+  public int getFunctionArity()
+  {
+    return getFunctionArity(pointer);
+  }
+
+  private native int getFunctionArity(long pointer);
+
+  /**
+   * @return the domain sorts of a function sort
+   */
+  public Sort[] getFunctionDomainSorts()
+  {
+    long[] pointers = getFunctionDomainSorts(pointer);
+    return Utils.getSorts(solver, pointers);
+  }
+
+  private native long[] getFunctionDomainSorts(long pointer);
+
+  /**
+   * @return the codomain sort of a function sort
+   */
+  public Sort getFunctionCodomainSort()
+  {
+    long sortPointer = getFunctionCodomainSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getFunctionCodomainSort(long pointer);
+
+  /* Array sort ---------------------------------------------------------- */
+
+  /**
+   * @return the array index sort of an array sort
+   */
+  public Sort getArrayIndexSort()
+  {
+    long sortPointer = getArrayIndexSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getArrayIndexSort(long pointer);
+
+  /**
+   * @return the array element sort of an array element sort
+   */
+  public Sort getArrayElementSort()
+  {
+    long sortPointer = getArrayElementSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getArrayElementSort(long pointer);
+
+  /* Set sort ------------------------------------------------------------ */
+
+  /**
+   * @return the element sort of a set sort
+   */
+  public Sort getSetElementSort()
+  {
+    long sortPointer = getSetElementSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getSetElementSort(long pointer);
+
+  /* Bag sort ------------------------------------------------------------ */
+
+  /**
+   * @return the element sort of a bag sort
+   */
+  public Sort getBagElementSort()
+  {
+    long sortPointer = getBagElementSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getBagElementSort(long pointer);
+
+  /* Sequence sort ------------------------------------------------------- */
+
+  /**
+   * @return the element sort of a sequence sort
+   */
+  public Sort getSequenceElementSort()
+  {
+    long sortPointer = getSequenceElementSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getSequenceElementSort(long pointer);
+
+  /* Uninterpreted sort -------------------------------------------------- */
+
+  /**
+   * @return the name of an uninterpreted sort
+   */
+  public String getUninterpretedSortName()
+  {
+    return getUninterpretedSortName(pointer);
+  }
+
+  private native String getUninterpretedSortName(long pointer);
+
+  /**
+   * @return true if an uninterpreted sort is parameterezied
+   */
+  public boolean isUninterpretedSortParameterized()
+  {
+    return isUninterpretedSortParameterized(pointer);
+  }
+
+  private native boolean isUninterpretedSortParameterized(long pointer);
+
+  /**
+   * @return the parameter sorts of an uninterpreted sort
+   */
+  public Sort[] getUninterpretedSortParamSorts()
+  {
+    long[] pointers = getUninterpretedSortParamSorts(pointer);
+    return Utils.getSorts(solver, pointers);
+  }
+
+  private native long[] getUninterpretedSortParamSorts(long pointer);
+
+  /* Sort constructor sort ----------------------------------------------- */
+
+  /**
+   * @return the name of a sort constructor sort
+   */
+  public String getSortConstructorName()
+  {
+    return getSortConstructorName(pointer);
+  }
+
+  private native String getSortConstructorName(long pointer);
+
+  /**
+   * @return the arity of a sort constructor sort
+   */
+  public int getSortConstructorArity()
+  {
+    return getSortConstructorArity(pointer);
+  }
+
+  private native int getSortConstructorArity(long pointer);
+
+  /* Bit-vector sort ----------------------------------------------------- */
+
+  /**
+   * @return the bit-width of the bit-vector sort
+   */
+  public int getBitVectorSize()
+  {
+    return getBitVectorSize(pointer);
+  }
+
+  private native int getBitVectorSize(long pointer);
+
+  /* Floating-point sort ------------------------------------------------- */
+
+  /**
+   * @return the bit-width of the exponent of the floating-point sort
+   */
+  public int getFloatingPointExponentSize()
+  {
+    return getFloatingPointExponentSize(pointer);
+  }
+
+  private native int getFloatingPointExponentSize(long pointer);
+
+  /**
+   * @return the width of the significand of the floating-point sort
+   */
+  public int getFloatingPointSignificandSize()
+  {
+    return getFloatingPointSignificandSize(pointer);
+  }
+
+  private native int getFloatingPointSignificandSize(long pointer);
+
+  /* Datatype sort ------------------------------------------------------- */
+
+  /**
+   * @return the parameter sorts of a datatype sort
+   */
+  public Sort[] getDatatypeParamSorts()
+  {
+    long[] pointers = getDatatypeParamSorts(pointer);
+    return Utils.getSorts(solver, pointers);
+  }
+
+  private native long[] getDatatypeParamSorts(long pointer);
+
+  /**
+   * @return the arity of a datatype sort
+   */
+  public int getDatatypeArity()
+  {
+    return getDatatypeArity(pointer);
+  }
+
+  private native int getDatatypeArity(long pointer);
+
+  /* Tuple sort ---------------------------------------------------------- */
+
+  /**
+   * @return the length of a tuple sort
+   */
+  public int getTupleLength()
+  {
+    return getTupleLength(pointer);
+  }
+
+  private native int getTupleLength(long pointer);
+
+  /**
+   * @return the element sorts of a tuple sort
+   */
+  public Sort[] getTupleSorts()
+  {
+    long[] pointers = getTupleSorts(pointer);
+    return Utils.getSorts(solver, pointers);
+  }
+
+  private native long[] getTupleSorts(long pointer);
+}
\ No newline at end of file
diff --git a/src/api/java/io/github/cvc5/api/Stat.java b/src/api/java/io/github/cvc5/api/Stat.java
new file mode 100644 (file)
index 0000000..c0c81c4
--- /dev/null
@@ -0,0 +1,165 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.util.Map;
+
+/**
+ * Represents a snapshot of a single statistic value.
+ * A value can be of type {@code long}, {@code double}, {@code String} or a histogram
+ * ({@code Map<String, Long>}).
+ * The value type can be queried (using {@code isInt()}, {@code isDouble()}, etc.) and
+ * the stored value can be accessed (using {@code getInt()}, {@code getDouble()}, etc.).
+ * It is possible to query whether this statistic is an expert statistic by
+ * {@code isExpert()} and whether its value is the default value by {@code isDefault()}.
+ */
+public class Stat extends AbstractPointer
+{
+  // region construction and destruction
+  Stat(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * @return a string representation of this Stat
+   */
+  protected native String toString(long pointer);
+
+  /**
+   * Is this value intended for experts only?
+   * @return Whether this is an expert statistic.
+   */
+  public boolean isExpert()
+  {
+    return isExpert(pointer);
+  }
+
+  private native boolean isExpert(long pointer);
+
+  /**
+   * Does this value hold the default value?
+   * @return Whether this is a defaulted statistic.
+   */
+  public boolean isDefault()
+  {
+    return isDefault(pointer);
+  }
+
+  private native boolean isDefault(long pointer);
+
+  /**
+   * Is this value an integer?
+   * @return Whether the value is an integer.
+   */
+  public boolean isInt()
+  {
+    return isInt(pointer);
+  }
+
+  private native boolean isInt(long pointer);
+
+  /**
+   * Return the integer value.
+   * @return The integer value.
+   */
+  public long getInt()
+  {
+    return getInt(pointer);
+  }
+
+  private native long getInt(long pointer);
+
+  /**
+   * Is this value a double?
+   * @return Whether the value is a double.
+   */
+  public boolean isDouble()
+  {
+    return isDouble(pointer);
+  }
+
+  private native boolean isDouble(long pointer);
+
+  /**
+   * Return the double value.
+   * @return The double value.
+   */
+  public double getDouble()
+  {
+    return getDouble(pointer);
+  }
+
+  private native double getDouble(long pointer);
+
+  /**
+   * Is this value a string?
+   * @return Whether the value is a string.
+   */
+  public boolean isString()
+  {
+    return isString(pointer);
+  }
+
+  private native boolean isString(long pointer);
+
+  /**
+   * Return the string value.
+   * @return The string value.
+   */
+  public String getString()
+  {
+    return getString(pointer);
+  }
+
+  private native String getString(long pointer);
+
+  /**
+   * Is this value a histogram?
+   * @return Whether the value is a histogram.
+   */
+  public boolean isHistogram()
+  {
+    return isHistogram(pointer);
+  }
+
+  private native boolean isHistogram(long pointer);
+
+  /**
+   * Return the histogram value.
+   * @return The histogram value.
+   */
+  public Map<String, Long> getHistogram()
+  {
+    return getHistogram(pointer);
+  }
+
+  private native Map<String, Long> getHistogram(long pointer);
+};
diff --git a/src/api/java/io/github/cvc5/api/Statistics.java b/src/api/java/io/github/cvc5/api/Statistics.java
new file mode 100644 (file)
index 0000000..c874e48
--- /dev/null
@@ -0,0 +1,121 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.util.Iterator;
+import java.util.NoSuchElementException;
+
+public class Statistics extends AbstractPointer implements Iterable<Pair<String, Stat>>
+{
+  // region construction and destruction
+  Statistics(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * @return a string representation of this Statistics
+   */
+  protected native String toString(long pointer);
+
+  /**
+   * Retrieve the statistic with the given name.
+   * Asserts that a statistic with the given name actually exists and throws
+   * a `CVC5ApiRecoverableException` if it does not.
+   * @param name Name of the statistic.
+   * @return The statistic with the given name.
+   */
+  public Stat get(String name)
+  {
+    long statPointer = get(pointer, name);
+    return new Stat(solver, statPointer);
+  }
+
+  private native long get(long pointer, String name);
+
+  /**
+   * Begin iteration over the statistics values.
+   * By default, only entries that are public (non-expert) and have been set
+   * are visible while the others are skipped.
+   * @param expert If set to true, expert statistics are shown as well.
+   * @param defaulted If set to true, defaulted statistics are shown as well.
+   */
+
+  private native long getIterator(long pointer);
+
+  private native boolean hasNext(long pointer, long iteratorPointer);
+
+  private native Pair<String, Long> getNext(long pointer, long iteratorPointer)
+      throws CVC5ApiException;
+
+  private native long increment(long pointer, long iteratorPointer) throws CVC5ApiException;
+
+  private native void deleteIteratorPointer(long iteratorPointer);
+
+  public class ConstIterator implements Iterator<Pair<String, Stat>>
+  {
+    private long iteratorPointer = 0;
+
+    public ConstIterator()
+    {
+      iteratorPointer = getIterator(pointer);
+    }
+
+    @Override public boolean hasNext()
+    {
+      return Statistics.this.hasNext(pointer, iteratorPointer);
+    }
+
+    @Override public Pair<String, Stat> next()
+    {
+      try
+      {
+        Pair<String, Long> pair = Statistics.this.getNext(pointer, iteratorPointer);
+        Stat stat = new Stat(solver, pair.second);
+        this.iteratorPointer = Statistics.this.increment(pointer, iteratorPointer);
+        return new Pair<>(pair.first, stat);
+      }
+      catch (CVC5ApiException e)
+      {
+        throw new NoSuchElementException(e.getMessage());
+      }
+    }
+
+    @Override public void finalize()
+    {
+      deleteIteratorPointer(iteratorPointer);
+    }
+  }
+
+  @Override public Iterator<Pair<String, Stat>> iterator()
+  {
+    return new ConstIterator();
+  }
+};
diff --git a/src/api/java/io/github/cvc5/api/Term.java b/src/api/java/io/github/cvc5/api/Term.java
new file mode 100644 (file)
index 0000000..7a1798b
--- /dev/null
@@ -0,0 +1,688 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.math.BigInteger;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.NoSuchElementException;
+import java.util.Set;
+
+public class Term extends AbstractPointer implements Comparable<Term>, Iterable<Term>
+{
+  // region construction and destruction
+  Term(Solver solver, long pointer)
+  {
+    super(solver, pointer);
+  }
+
+  protected static native void deletePointer(long pointer);
+
+  public long getPointer()
+  {
+    return pointer;
+  }
+
+  @Override public void finalize()
+  {
+    deletePointer(pointer);
+  }
+
+  // endregion
+
+  /**
+   * Syntactic equality operator.
+   * Return true if both terms are syntactically identical.
+   * Both terms must belong to the same solver object.
+   *
+   * @param t the term to compare to for equality
+   * @return true if the terms are equal
+   */
+  @Override public boolean equals(Object t)
+  {
+    if (this == t)
+      return true;
+    if (t == null || getClass() != t.getClass())
+      return false;
+    Term term = (Term) t;
+    if (this.pointer == term.pointer)
+    {
+      return true;
+    }
+    return equals(pointer, term.getPointer());
+  }
+
+  private native boolean equals(long pointer1, long pointer2);
+
+  /**
+   * Comparison for ordering on terms.
+   *
+   * @param t the term to compare to
+   * @return a negative integer, zero, or a positive integer as this term
+   * is less than, equal to, or greater than the specified term.
+   */
+  @Override public int compareTo(Term t)
+  {
+    return this.compareTo(pointer, t.getPointer());
+  }
+
+  private native int compareTo(long pointer1, long pointer2);
+
+  /**
+   * @return the number of children of this term
+   */
+  public int getNumChildren()
+  {
+    return getNumChildren(pointer);
+  }
+
+  private native int getNumChildren(long pointer);
+
+  /**
+   * Get the child term at a given index.
+   *
+   * @param index the index of the child term to return
+   * @return the child term with the given index
+   */
+  public Term getChild(int index) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(index, "index");
+    long termPointer = getChild(pointer, index);
+    return new Term(solver, termPointer);
+  }
+
+  private native long getChild(long pointer, int index);
+
+  /**
+   * @return the id of this term
+   */
+  public long getId()
+  {
+    return getId(pointer);
+  }
+
+  private native long getId(long pointer);
+
+  /**
+   * @return the kind of this term
+   */
+  public Kind getKind() throws CVC5ApiException
+  {
+    int value = getKind(pointer);
+    return Kind.fromInt(value);
+  }
+
+  private native int getKind(long pointer);
+
+  /**
+   * @return the sort of this term
+   */
+  public Sort getSort()
+  {
+    long sortPointer = getSort(pointer);
+    return new Sort(solver, sortPointer);
+  }
+
+  private native long getSort(long pointer);
+
+  /**
+   * @return the result of replacing 'term' by 'replacement' in this term
+   */
+  public Term substitute(Term term, Term replacement)
+  {
+    long termPointer = substitute(pointer, term.getPointer(), replacement.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long substitute(long pointer, long termPointer, long replacementPointer);
+
+  /**
+   * @return the result of simultaneously replacing 'terms' by 'replacements'
+   * in this term
+   */
+  public Term substitute(List<Term> terms, List<Term> replacements)
+  {
+    return substitute(terms.toArray(new Term[0]), replacements.toArray(new Term[0]));
+  }
+
+  /**
+   * @return the result of simultaneously replacing 'terms' by 'replacements'
+   * in this term
+   */
+  public Term substitute(Term[] terms, Term[] replacements)
+  {
+    long[] termPointers = new long[terms.length];
+    for (int i = 0; i < termPointers.length; i++)
+    {
+      termPointers[i] = terms[i].getPointer();
+    }
+    long[] replacementPointers = new long[replacements.length];
+    for (int i = 0; i < replacements.length; i++)
+    {
+      replacementPointers[i] = replacements[i].getPointer();
+    }
+
+    long termPointer = substitute(pointer, termPointers, replacementPointers);
+    return new Term(solver, termPointer);
+  }
+
+  private native long substitute(long pointer, long[] termPointers, long[] replacementPointers);
+
+  /**
+   * @return true iff this term has an operator
+   */
+  public boolean hasOp()
+  {
+    return hasOp(pointer);
+  }
+
+  private native boolean hasOp(long pointer);
+
+  /**
+   * @return the Op used to create this term
+   * Note: This is safe to call when hasOp() returns true.
+   */
+  public Op getOp()
+  {
+    long opPointer = getOp(pointer);
+    return new Op(solver, opPointer);
+  }
+
+  private native long getOp(long pointer);
+
+  /**
+   * @return true if this Term is a null term
+   */
+  public boolean isNull()
+  {
+    return isNull(pointer);
+  }
+
+  private native boolean isNull(long pointer);
+
+  /**
+   * Boolean negation.
+   *
+   * @return the Boolean negation of this term
+   */
+  public Term notTerm()
+  {
+    long termPointer = notTerm(pointer);
+    return new Term(solver, termPointer);
+  }
+
+  private native long notTerm(long pointer);
+
+  /**
+   * Boolean and.
+   *
+   * @param t a Boolean term
+   * @return the conjunction of this term and the given term
+   */
+  public Term andTerm(Term t)
+  {
+    long termPointer = andTerm(pointer, t.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long andTerm(long pointer, long termPointer);
+
+  /**
+   * Boolean or.
+   *
+   * @param t a Boolean term
+   * @return the disjunction of this term and the given term
+   */
+  public Term orTerm(Term t)
+  {
+    long termPointer = orTerm(pointer, t.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long orTerm(long pointer, long termPointer);
+
+  /**
+   * Boolean exclusive or.
+   *
+   * @param t a Boolean term
+   * @return the exclusive disjunction of this term and the given term
+   */
+  public Term xorTerm(Term t)
+  {
+    long termPointer = xorTerm(pointer, t.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long xorTerm(long pointer, long termPointer);
+
+  /**
+   * Equality.
+   *
+   * @param t a Boolean term
+   * @return the Boolean equivalence of this term and the given term
+   */
+  public Term eqTerm(Term t)
+  {
+    long termPointer = eqTerm(pointer, t.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long eqTerm(long pointer, long termPointer);
+
+  /**
+   * Boolean implication.
+   *
+   * @param t a Boolean term
+   * @return the implication of this term and the given term
+   */
+  public Term impTerm(Term t)
+  {
+    long termPointer = impTerm(pointer, t.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long impTerm(long pointer, long termPointer);
+
+  /**
+   * If-then-else with this term as the Boolean condition.
+   *
+   * @param thenTerm the 'then' term
+   * @param elseTerm the 'else' term
+   * @return the if-then-else term with this term as the Boolean condition
+   */
+  public Term iteTerm(Term thenTerm, Term elseTerm)
+  {
+    long termPointer = iteTerm(pointer, thenTerm.getPointer(), elseTerm.getPointer());
+    return new Term(solver, termPointer);
+  }
+
+  private native long iteTerm(long pointer, long thenPointer, long elsePointer);
+
+  /**
+   * @return a string representation of this term.
+   */
+  protected native String toString(long pointer);
+
+  /**
+   * @return true if the term is an integer value.
+   */
+  public boolean isIntegerValue()
+  {
+    return isIntegerValue(pointer);
+  }
+
+  private native boolean isIntegerValue(long pointer);
+
+  /**
+   * Asserts isIntegerValue().
+   * @return the integer represented by this term.
+   */
+  public BigInteger getIntegerValue()
+  {
+    return new BigInteger(getIntegerValue(pointer));
+  }
+
+  private native String getIntegerValue(long pointer);
+
+  /**
+   * @return true if the term is a string constant.
+   */
+  public boolean isStringValue()
+  {
+    return isStringValue(pointer);
+  }
+
+  private native boolean isStringValue(long pointer);
+
+  /**
+   * @return the stored string constant.
+   * <p>
+   * Note: This method is not to be confused with toString() which returns the
+   * term in some string representation, whatever data it may hold.
+   * Asserts isString().
+   */
+  public String getStringValue()
+  {
+    return getStringValue(pointer);
+  }
+
+  private native String getStringValue(long pointer);
+
+  /**
+   * @return true if the term is a rational value.
+   */
+  public boolean isRealValue()
+  {
+    return isRealValue(pointer);
+  }
+
+  private native boolean isRealValue(long pointer);
+
+  /**
+   * Asserts isRealValue().
+   * @return the representation of a rational value as a pair of its numerator
+   * and denominator.
+   */
+  public Pair<BigInteger, BigInteger> getRealValue()
+  {
+    String rational = getRealValue(pointer);
+    return Utils.getRational(rational);
+  }
+
+  private native String getRealValue(long pointer);
+
+  /**
+   * @return true if the term is a constant array.
+   */
+  public boolean isConstArray()
+  {
+    return isConstArray(pointer);
+  }
+
+  private native boolean isConstArray(long pointer);
+
+  /**
+   * Asserts isConstArray().
+   * @return the base (element stored at all indices) of a constant array
+   */
+  public Term getConstArrayBase()
+  {
+    long termPointer = getConstArrayBase(pointer);
+    return new Term(solver, termPointer);
+  }
+
+  private native long getConstArrayBase(long pointer);
+
+  /**
+   * @return true if the term is a Boolean value.
+   */
+  public boolean isBooleanValue()
+  {
+    return isBooleanValue(pointer);
+  }
+
+  private native boolean isBooleanValue(long pointer);
+  /**
+   * Asserts isBooleanValue().
+   * @return the representation of a Boolean value as a native Boolean value.
+   */
+  public boolean getBooleanValue()
+  {
+    return getBooleanValue(pointer);
+  }
+
+  private native boolean getBooleanValue(long pointer);
+
+  /**
+   * @return true if the term is a bit-vector value.
+   */
+  public boolean isBitVectorValue()
+  {
+    return isBitVectorValue(pointer);
+  }
+
+  private native boolean isBitVectorValue(long pointer);
+
+  /**
+   * Asserts isBitVectorValue().
+   * @return the representation of a bit-vector value in bit string representation.
+   */
+  public String getBitVectorValue() throws CVC5ApiException
+  {
+    return getBitVectorValue(2);
+  }
+
+  /**
+   * Asserts isBitVectorValue().
+   * @return the representation of a bit-vector value in string representation.
+   * Supported bases are 2 (bit string), 10 (decimal string) or 16 (hexadecimal
+   * string).
+   */
+  public String getBitVectorValue(int base) throws CVC5ApiException
+  {
+    Utils.validateUnsigned(base, "base");
+    return getBitVectorValue(pointer, base);
+  }
+
+  private native String getBitVectorValue(long pointer, int base);
+
+  /**
+   * @return true if the term is an abstract value.
+   */
+  public boolean isAbstractValue()
+  {
+    return isAbstractValue(pointer);
+  }
+
+  private native boolean isAbstractValue(long pointer);
+
+  /**
+   * Asserts isAbstractValue().
+   * @return the representation of an abstract value as a string.
+   */
+  public String getAbstractValue()
+  {
+    return getAbstractValue(pointer);
+  }
+
+  private native String getAbstractValue(long pointer);
+
+  /**
+   * @return true if the term is a tuple value.
+   */
+  public boolean isTupleValue()
+  {
+    return isTupleValue(pointer);
+  }
+
+  private native boolean isTupleValue(long pointer);
+
+  /**
+   * Asserts isTupleValue().
+   * @return the representation of a tuple value as a vector of terms.
+   */
+  public Term[] getTupleValue()
+  {
+    long[] termPointers = getTupleValue(pointer);
+    return Utils.getTerms(solver, termPointers);
+  }
+
+  private native long[] getTupleValue(long pointer);
+
+  /**
+   * @return true if the term is the floating-point value for positive zero.
+   */
+  public boolean isFloatingPointPosZero()
+  {
+    return isFloatingPointPosZero(pointer);
+  }
+
+  private native boolean isFloatingPointPosZero(long pointer);
+  /**
+   * @return true if the term is the floating-point value for negative zero.
+   */
+  public boolean isFloatingPointNegZero()
+  {
+    return isFloatingPointNegZero(pointer);
+  }
+
+  private native boolean isFloatingPointNegZero(long pointer);
+  /**
+   * @return true if the term is the floating-point value for positive
+   * infinity.
+   */
+  public boolean isFloatingPointPosInf()
+  {
+    return isFloatingPointPosInf(pointer);
+  }
+
+  private native boolean isFloatingPointPosInf(long pointer);
+  /**
+   * @return true if the term is the floating-point value for negative
+   * infinity.
+   */
+  public boolean isFloatingPointNegInf()
+  {
+    return isFloatingPointNegInf(pointer);
+  }
+
+  private native boolean isFloatingPointNegInf(long pointer);
+  /**
+   * @return true if the term is the floating-point value for not a number.
+   */
+  public boolean isFloatingPointNaN()
+  {
+    return isFloatingPointNaN(pointer);
+  }
+
+  private native boolean isFloatingPointNaN(long pointer);
+  /**
+   * @return true if the term is a floating-point value.
+   */
+  public boolean isFloatingPointValue()
+  {
+    return isFloatingPointValue(pointer);
+  }
+
+  private native boolean isFloatingPointValue(long pointer);
+  /**
+   * Asserts isFloatingPointValue().
+   * @return the representation of a floating-point value as a tuple of the
+   * exponent width, the significand width and a bit-vector value.
+   */
+  public Triplet<Long, Long, Term> getFloatingPointValue()
+  {
+    Triplet<Long, Long, Long> triplet = getFloatingPointValue(pointer);
+    return new Triplet(triplet.first, triplet.second, new Term(solver, triplet.third));
+  }
+
+  private native Triplet<Long, Long, Long> getFloatingPointValue(long pointer);
+
+  /**
+   * @return true if the term is a set value.
+   */
+  public boolean isSetValue()
+  {
+    return isSetValue(pointer);
+  }
+
+  private native boolean isSetValue(long pointer);
+  /**
+   * Asserts isSetValue().
+   * @return the representation of a set value as a set of terms.
+   */
+  public Set<Term> getSetValue()
+  {
+    long[] termPointers = getSetValue(pointer);
+    Term[] terms = Utils.getTerms(solver, termPointers);
+    return new HashSet<Term>(Arrays.asList(terms));
+  }
+
+  private native long[] getSetValue(long pointer);
+
+  /**
+   * @return true if the term is a sequence value.
+   */
+  public boolean isSequenceValue()
+  {
+    return isSequenceValue(pointer);
+  }
+
+  private native boolean isSequenceValue(long pointer);
+
+  /**
+   * Asserts isSequenceValue().
+   * Note that it is usually necessary for sequences to call
+   * `Solver::simplify()` to turn a sequence that is constructed by, e.g.,
+   * concatenation of unit sequences, into a sequence value.
+   * @return the representation of a sequence value as a vector of terms.
+   */
+  public Term[] getSequenceValue()
+  {
+    long[] termPointers = getSequenceValue(pointer);
+    return Utils.getTerms(solver, termPointers);
+  }
+
+  private native long[] getSequenceValue(long pointer);
+
+  /**
+   * @return true if the term is a value from an uninterpreted sort.
+   */
+  public boolean isUninterpretedValue()
+  {
+    return isUninterpretedValue(pointer);
+  }
+
+  private native boolean isUninterpretedValue(long pointer);
+
+  /**
+  boolean @return()
+   * Asserts isUninterpretedValue().
+   * @return the representation of an uninterpreted value as a pair of its
+  sort and its
+   * index.
+   */
+  public Pair<Sort, Integer> getUninterpretedValue()
+  {
+    Pair<Long, Integer> pair = getUninterpretedValue(pointer);
+    Sort sort = new Sort(solver, pair.first);
+    return new Pair<Sort, Integer>(sort, pair.second);
+  }
+
+  private native Pair<Long, Integer> getUninterpretedValue(long pointer);
+
+  public class ConstIterator implements Iterator<Term>
+  {
+    private int currentIndex;
+    private int size;
+
+    public ConstIterator()
+    {
+      currentIndex = -1;
+      size = getNumChildren();
+    }
+
+    @Override public boolean hasNext()
+    {
+      return currentIndex < size - 1;
+    }
+
+    @Override public Term next()
+    {
+      if (currentIndex >= size - 1)
+      {
+        throw new NoSuchElementException();
+      }
+      currentIndex++;
+      try
+      {
+        return getChild(currentIndex);
+      }
+      catch (CVC5ApiException e)
+      {
+        e.printStackTrace();
+        throw new RuntimeException(e.getMessage());
+      }
+    }
+  }
+
+  @Override public Iterator<Term> iterator()
+  {
+    return new ConstIterator();
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/Triplet.java b/src/api/java/io/github/cvc5/api/Triplet.java
new file mode 100644 (file)
index 0000000..b9cd36d
--- /dev/null
@@ -0,0 +1,41 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+public class Triplet<A, B, C>
+{
+  public A first;
+  public B second;
+  public C third;
+  public Triplet(A first, B second, C third)
+  {
+    this.first = first;
+    this.second = second;
+    this.third = third;
+  }
+
+  @Override public boolean equals(Object object)
+  {
+    if (this == object)
+      return true;
+    if (object == null || getClass() != object.getClass())
+      return false;
+
+    Triplet<A, B, C> triplet = (Triplet<A, B, C>) object;
+    return this.first.equals(triplet.first) && this.second.equals(triplet.second)
+        && this.third.equals(triplet.third);
+  }
+}
diff --git a/src/api/java/io/github/cvc5/api/Utils.java b/src/api/java/io/github/cvc5/api/Utils.java
new file mode 100644 (file)
index 0000000..54e0c9c
--- /dev/null
@@ -0,0 +1,221 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 java API.
+ */
+
+package io.github.cvc5.api;
+
+import java.io.IOException;
+import java.math.BigInteger;
+import java.util.ArrayList;
+import java.util.List;
+
+public class Utils
+{
+  static
+  {
+    loadLibraries();
+  }
+
+  /**
+   * load cvc5 jni library
+   */
+  public static void loadLibraries()
+  {
+    System.loadLibrary("cvc5jni");
+  }
+
+  /**
+   * return sorts array from array of pointers
+   */
+  public static Sort[] getSorts(Solver solver, long[] pointers)
+  {
+    Sort[] sorts = new Sort[pointers.length];
+    for (int i = 0; i < pointers.length; i++)
+    {
+      sorts[i] = new Sort(solver, pointers[i]);
+    }
+    return sorts;
+  }
+
+  /**
+   * return terms array from array of pointers
+   */
+  public static Term[] getTerms(Solver solver, long[] pointers)
+  {
+    Term[] terms = new Term[pointers.length];
+    for (int i = 0; i < pointers.length; i++)
+    {
+      terms[i] = new Term(solver, pointers[i]);
+    }
+    return terms;
+  }
+
+  /**
+   * get pointers from one dimensional array
+   */
+  public static long[] getPointers(IPointer[] objects)
+  {
+    long[] pointers = new long[objects.length];
+    for (int i = 0; i < pointers.length; i++)
+    {
+      pointers[i] = objects[i].getPointer();
+    }
+    return pointers;
+  }
+
+  /**
+   * get pointers from two dimensional matrix
+   */
+  public static long[][] getPointers(IPointer[][] objects)
+  {
+    long[][] pointers = new long[objects.length][];
+    for (int i = 0; i < pointers.length; i++)
+    {
+      pointers[i] = new long[objects[i].length];
+      for (int j = 0; j < objects[i].length; j++)
+      {
+        pointers[i][j] = objects[i][j].getPointer();
+      }
+    }
+    return pointers;
+  }
+
+  public static void validateUnsigned(int integer, String name) throws CVC5ApiException
+  {
+    if (integer < 0)
+    {
+      throw new CVC5ApiException("Expected " + name + " '" + integer + "' to be non negative.");
+    }
+  }
+
+  public static void validateUnsigned(long integer, String name) throws CVC5ApiException
+  {
+    if (integer < 0)
+    {
+      throw new CVC5ApiException("Expected " + name + " '" + integer + "' to be non negative.");
+    }
+  }
+
+  public static void validateUnsigned(int[] integers, String name) throws CVC5ApiException
+  {
+    for (int i = 0; i < integers.length; i++)
+    {
+      if (integers[i] < 0)
+      {
+        throw new CVC5ApiException(
+            "Expected " + name + "[" + i + "] '" + integers[i] + "' to be non negative.");
+      }
+    }
+  }
+
+  public static void validateUnsigned(long[] integers, String name) throws CVC5ApiException
+  {
+    for (int i = 0; i < integers.length; i++)
+    {
+      if (integers[i] < 0)
+      {
+        throw new CVC5ApiException(
+            "Expected " + name + "[" + i + "] '" + integers[i] + "' to be non negative.");
+      }
+    }
+  }
+
+  public static <K> Pair<K, Long>[] getPairs(Pair<K, ? extends AbstractPointer>[] abstractPointers)
+  {
+    Pair<K, Long>[] pointers = new Pair[abstractPointers.length];
+    for (int i = 0; i < pointers.length; i++)
+    {
+      pointers[i] = new Pair<>(abstractPointers[i].first, abstractPointers[i].second.getPointer());
+    }
+    return pointers;
+  }
+
+  /**
+    Convert a rational string a/b to a pair of BigIntegers
+  */
+  public static Pair<BigInteger, BigInteger> getRational(String rational)
+  {
+    if (rational.contains("/"))
+    {
+      String[] pair = rational.split("/");
+      return new Pair<>(new BigInteger(pair[0]), new BigInteger(pair[1]));
+    }
+    return new Pair<>(new BigInteger(rational), new BigInteger("1"));
+  }
+
+  /**
+     Convert a pair of BigIntegers to a rational string a/b
+   */
+  public static String getRational(Pair<BigInteger, BigInteger> pair)
+  {
+    return pair.first.toString() + "/" + pair.second.toString();
+  }
+
+  /**
+   * Get the string version of define-fun command.
+   * @param f the function to print
+   * @param params the function parameters
+   * @param body the function body
+   * @return a string version of define-fun
+   */
+  private static String defineFunToString(Term f, Term[] params, Term body)
+  {
+    Sort sort = f.getSort();
+    if (sort.isFunction())
+    {
+      sort = sort.getFunctionCodomainSort();
+    }
+    StringBuilder ss = new StringBuilder();
+    ss.append("(define-fun ").append(f).append(" (");
+    for (int i = 0; i < params.length; ++i)
+    {
+      if (i > 0)
+      {
+        ss.append(' ');
+      }
+      ss.append('(').append(params[i]).append(' ').append(params[i].getSort()).append(')');
+    }
+    ss.append(") ").append(sort).append(' ').append(body).append(')');
+    return ss.toString();
+  }
+
+  /**
+   * Print solutions for synthesis conjecture to the standard output stream.
+   * @param terms the terms for which the synthesis solutions were retrieved
+   * @param sols the synthesis solutions of the given terms
+   */
+  public static void printSynthSolutions(Term[] terms, Term[] sols) throws CVC5ApiException
+  {
+    System.out.println('(');
+
+    for (int i = 0; i < terms.length; ++i)
+    {
+      List<Term> params = new ArrayList<>();
+      Term body = null;
+      if (sols[i].getKind() == Kind.LAMBDA)
+      {
+        for (Term t : sols[i].getChild(0))
+        {
+          params.add(t);
+        }
+        body = sols[i].getChild(1);
+      }
+      if (body != null)
+      {
+        System.out.println("  " + defineFunToString(terms[i], params.toArray(new Term[0]), body));
+      }
+    }
+    System.out.println(')');
+  }
+}
diff --git a/src/api/java/jni/api_utilities.cpp b/src/api/java/jni/api_utilities.cpp
new file mode 100644 (file)
index 0000000..8827b50
--- /dev/null
@@ -0,0 +1,52 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api_utilities.h"
+
+#include <string>
+#include <vector>
+
+jobjectArray getStringArrayFromStringVector(
+    JNIEnv* env, const std::vector<std::string>& cStrings)
+{
+  jclass stringClass = env->FindClass("java/lang/String");
+  jobjectArray ret =
+      env->NewObjectArray(cStrings.size(), stringClass, env->NewStringUTF(""));
+  for (size_t i = 0; i < cStrings.size(); i++)
+  {
+    jstring jString = env->NewStringUTF(cStrings[i].c_str());
+    env->SetObjectArrayElement(ret, i, jString);
+  }
+  return ret;
+}
+
+jobject getDoubleObject(JNIEnv* env, double cValue)
+{
+  jdouble jValue = static_cast<jdouble>(cValue);
+  jclass doubleClass = env->FindClass("java/lang/Double");
+  jmethodID methodId = env->GetMethodID(doubleClass, "<init>", "(D)V");
+  jobject ret = env->NewObject(doubleClass, methodId, jValue);
+  return ret;
+}
+
+jobject getBooleanObject(JNIEnv* env, bool cValue)
+{
+  jboolean jValue = static_cast<jboolean>(cValue);
+  jclass booleanClass = env->FindClass("Ljava/lang/Boolean;");
+  jmethodID booleanConstructor =
+      env->GetMethodID(booleanClass, "<init>", "(Z)V");
+  jobject ret = env->NewObject(booleanClass, booleanConstructor, jValue);
+  return ret;
+}
\ No newline at end of file
diff --git a/src/api/java/jni/api_utilities.h b/src/api/java/jni/api_utilities.h
new file mode 100644 (file)
index 0000000..08c315e
--- /dev/null
@@ -0,0 +1,142 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#ifndef CVC5__API_UTILITIES_H
+#define CVC5__API_UTILITIES_H
+
+#include <jni.h>
+
+#include <string>
+#include <vector>
+
+#define CVC5_JAVA_API_TRY_CATCH_BEGIN \
+  try                                 \
+  {
+#define CVC5_JAVA_API_TRY_CATCH_END(env)                                  \
+  }                                                                       \
+  catch (const CVC5ApiOptionException& e)                                 \
+  {                                                                       \
+    jclass exceptionClass =                                               \
+        env->FindClass("io/github/cvc5/api/CVC5ApiOptionException");      \
+    env->ThrowNew(exceptionClass, e.what());                              \
+  }                                                                       \
+  catch (const CVC5ApiRecoverableException& e)                            \
+  {                                                                       \
+    jclass exceptionClass =                                               \
+        env->FindClass("io/github/cvc5/api/CVC5ApiRecoverableException"); \
+    env->ThrowNew(exceptionClass, e.what());                              \
+  }                                                                       \
+  catch (const CVC5ApiException& e)                                       \
+  {                                                                       \
+    jclass exceptionClass =                                               \
+        env->FindClass("io/github/cvc5/api/CVC5ApiException");            \
+    env->ThrowNew(exceptionClass, e.what());                              \
+  }
+#define CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, returnValue) \
+  CVC5_JAVA_API_TRY_CATCH_END(env)                           \
+  return returnValue;
+
+/**
+ * Convert pointers coming from Java to cvc5 objects
+ * @tparam T cvc5 class (Term, Sort, Grammar, etc)
+ * @param env jni environment
+ * @param jPointers pointers coming from java
+ * @return a vector of cvc5 objects
+ */
+template <class T>
+std::vector<T> getObjectsFromPointers(JNIEnv* env, jlongArray jPointers)
+{
+  // get the size of pointers
+  jsize size = env->GetArrayLength(jPointers);
+  // allocate a buffer for c pointers
+  std::vector<jlong> cPointers(size);
+  // copy java array to the buffer
+  env->GetLongArrayRegion(jPointers, 0, size, cPointers.data());
+  // copy the terms into a vector
+  std::vector<T> objects;
+  for (jlong pointer : cPointers)
+  {
+    T* term = reinterpret_cast<T*>(pointer);
+    objects.push_back(*term);
+  }
+  return objects;
+}
+
+/**
+ * Convert cvc5 objects into pointers
+ * @tparam T cvc5 class (Term, Sort, Grammar, etc)
+ * @param env jni environment
+ * @param objects cvc5 objects
+ * @return jni array of pointers
+ */
+template <class T>
+jlongArray getPointersFromObjects(JNIEnv* env, const std::vector<T>& objects)
+{
+  std::vector<jlong> pointers(objects.size());
+  for (size_t i = 0; i < objects.size(); i++)
+  {
+    pointers[i] = reinterpret_cast<jlong>(new T(objects[i]));
+  }
+  jlongArray ret = env->NewLongArray(objects.size());
+  env->SetLongArrayRegion(ret, 0, objects.size(), pointers.data());
+  return ret;
+}
+
+/**
+ * Convert a cpp signed (unsigned) integer to an object of BigInteger class
+ * @tparam T cpp types (int64_t, uint64_t, int32_t, int32_t, etc)
+ * @param env jni environment
+ * @param value cpp integer value
+ * @return an object of java BigInteger
+ */
+template <class T>
+jobject getBigIntegerObject(JNIEnv* env, T value)
+{
+  std::string s = std::to_string(value);
+  jstring javaString = env->NewStringUTF(s.c_str());
+  jclass bigIntegerClass = env->FindClass("java/math/BigInteger");
+  jmethodID bigIntegerConstructor =
+      env->GetMethodID(bigIntegerClass, "<init>", "(Ljava/lang/String;)V");
+  jobject ret =
+      env->NewObject(bigIntegerClass, bigIntegerConstructor, javaString);
+  return ret;
+}
+
+/**
+ * Generate an array of java strings from a vector of cpp strings
+ * @param env jni environment
+ * @param cStrings a vector of strings
+ * @return an array of java strings
+ */
+jobjectArray getStringArrayFromStringVector(
+    JNIEnv* env, const std::vector<std::string>& cStrings);
+
+/**
+ * Generate a Double object from cpp double value
+ * @param env jni environment
+ * @param value
+ * @return a Double object
+ */
+jobject getDoubleObject(JNIEnv* env, double value);
+
+/**
+ * Generate a Boolean object from cpp bool value
+ * @param env jni environment
+ * @param value
+ * @return a Boolean object
+ */
+jobject getBooleanObject(JNIEnv* env, bool value);
+
+#endif  // CVC5__API_UTILITIES_H
diff --git a/src/api/java/jni/cvc5JavaApi.cpp b/src/api/java/jni/cvc5JavaApi.cpp
deleted file mode 100644 (file)
index 378fa09..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5JavaApi.h"
-
-#include <string>
-#include <vector>
-
-jobjectArray getStringArrayFromStringVector(
-    JNIEnv* env, const std::vector<std::string>& cStrings)
-{
-  jclass stringClass = env->FindClass("java/lang/String");
-  jobjectArray ret =
-      env->NewObjectArray(cStrings.size(), stringClass, env->NewStringUTF(""));
-  for (size_t i = 0; i < cStrings.size(); i++)
-  {
-    jstring jString = env->NewStringUTF(cStrings[i].c_str());
-    env->SetObjectArrayElement(ret, i, jString);
-  }
-  return ret;
-}
-
-jobject getDoubleObject(JNIEnv* env, double cValue)
-{
-  jdouble jValue = static_cast<jdouble>(cValue);
-  jclass doubleClass = env->FindClass("java/lang/Double");
-  jmethodID methodId = env->GetMethodID(doubleClass, "<init>", "(D)V");
-  jobject ret = env->NewObject(doubleClass, methodId, jValue);
-  return ret;
-}
-
-jobject getBooleanObject(JNIEnv* env, bool cValue)
-{
-  jboolean jValue = static_cast<jboolean>(cValue);
-  jclass booleanClass = env->FindClass("Ljava/lang/Boolean;");
-  jmethodID booleanConstructor =
-      env->GetMethodID(booleanClass, "<init>", "(Z)V");
-  jobject ret = env->NewObject(booleanClass, booleanConstructor, jValue);
-  return ret;
-}
\ No newline at end of file
diff --git a/src/api/java/jni/cvc5JavaApi.h b/src/api/java/jni/cvc5JavaApi.h
deleted file mode 100644 (file)
index 73f2fb3..0000000
+++ /dev/null
@@ -1,140 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#ifndef CVC5__JAVA_API_H
-#define CVC5__JAVA_API_H
-
-#include <jni.h>
-
-#include <string>
-#include <vector>
-
-#define CVC5_JAVA_API_TRY_CATCH_BEGIN \
-  try                                 \
-  {
-#define CVC5_JAVA_API_TRY_CATCH_END(env)                                   \
-  }                                                                        \
-  catch (const CVC5ApiOptionException& e)                                  \
-  {                                                                        \
-    jclass exceptionClass = env->FindClass("cvc5/CVC5ApiOptionException"); \
-    env->ThrowNew(exceptionClass, e.what());                               \
-  }                                                                        \
-  catch (const CVC5ApiRecoverableException& e)                             \
-  {                                                                        \
-    jclass exceptionClass =                                                \
-        env->FindClass("cvc5/CVC5ApiRecoverableException");                \
-    env->ThrowNew(exceptionClass, e.what());                               \
-  }                                                                        \
-  catch (const CVC5ApiException& e)                                        \
-  {                                                                        \
-    jclass exceptionClass = env->FindClass("cvc5/CVC5ApiException");       \
-    env->ThrowNew(exceptionClass, e.what());                               \
-  }
-#define CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, returnValue) \
-  CVC5_JAVA_API_TRY_CATCH_END(env)                           \
-  return returnValue;
-
-/**
- * Convert pointers coming from Java to cvc5 objects
- * @tparam T cvc5 class (Term, Sort, Grammar, etc)
- * @param env jni environment
- * @param jPointers pointers coming from java
- * @return a vector of cvc5 objects
- */
-template <class T>
-std::vector<T> getObjectsFromPointers(JNIEnv* env, jlongArray jPointers)
-{
-  // get the size of pointers
-  jsize size = env->GetArrayLength(jPointers);
-  // allocate a buffer for c pointers
-  std::vector<jlong> cPointers(size);
-  // copy java array to the buffer
-  env->GetLongArrayRegion(jPointers, 0, size, cPointers.data());
-  // copy the terms into a vector
-  std::vector<T> objects;
-  for (jlong pointer : cPointers)
-  {
-    T* term = reinterpret_cast<T*>(pointer);
-    objects.push_back(*term);
-  }
-  return objects;
-}
-
-/**
- * Convert cvc5 objects into pointers
- * @tparam T cvc5 class (Term, Sort, Grammar, etc)
- * @param env jni environment
- * @param objects cvc5 objects
- * @return jni array of pointers
- */
-template <class T>
-jlongArray getPointersFromObjects(JNIEnv* env, const std::vector<T>& objects)
-{
-  std::vector<jlong> pointers(objects.size());
-  for (size_t i = 0; i < objects.size(); i++)
-  {
-    pointers[i] = reinterpret_cast<jlong>(new T(objects[i]));
-  }
-  jlongArray ret = env->NewLongArray(objects.size());
-  env->SetLongArrayRegion(ret, 0, objects.size(), pointers.data());
-  return ret;
-}
-
-/**
- * Convert a cpp signed (unsigned) integer to an object of BigInteger class
- * @tparam T cpp types (int64_t, uint64_t, int32_t, int32_t, etc)
- * @param env jni environment
- * @param value cpp integer value
- * @return an object of java BigInteger
- */
-template <class T>
-jobject getBigIntegerObject(JNIEnv* env, T value)
-{
-  std::string s = std::to_string(value);
-  jstring javaString = env->NewStringUTF(s.c_str());
-  jclass bigIntegerClass = env->FindClass("java/math/BigInteger");
-  jmethodID bigIntegerConstructor =
-      env->GetMethodID(bigIntegerClass, "<init>", "(Ljava/lang/String;)V");
-  jobject ret =
-      env->NewObject(bigIntegerClass, bigIntegerConstructor, javaString);
-  return ret;
-}
-
-/**
- * Generate an array of java strings from a vector of cpp strings
- * @param env jni environment
- * @param cStrings a vector of strings
- * @return an array of java strings
- */
-jobjectArray getStringArrayFromStringVector(
-    JNIEnv* env, const std::vector<std::string>& cStrings);
-
-/**
- * Generate a Double object from cpp double value
- * @param env jni environment
- * @param value
- * @return a Double object
- */
-jobject getDoubleObject(JNIEnv* env, double value);
-
-/**
- * Generate a Boolean object from cpp bool value
- * @param env jni environment
- * @param value
- * @return a Boolean object
- */
-jobject getBooleanObject(JNIEnv* env, bool value);
-
-#endif  // CVC5__JAVA_API_H
\ No newline at end of file
diff --git a/src/api/java/jni/cvc5_Datatype.cpp b/src/api/java/jni/cvc5_Datatype.cpp
deleted file mode 100644 (file)
index eb834da..0000000
+++ /dev/null
@@ -1,255 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Datatype.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Datatype
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Datatype_deletePointer(JNIEnv* env,
-                                                        jclass,
-                                                        jlong pointer)
-{
-  delete ((Datatype*)pointer);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    getConstructor
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Datatype_getConstructor__JI(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer,
-                                                              jint idx)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  DatatypeConstructor* retPointer =
-      new DatatypeConstructor(current->operator[](idx));
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    getConstructor
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Datatype_getConstructor__JLjava_lang_String_2(
-    JNIEnv* env, jobject, jlong pointer, jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  DatatypeConstructor* retPointer =
-      new DatatypeConstructor(current->operator[](cName));
-  env->ReleaseStringUTFChars(jName, s);
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    getConstructorTerm
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Datatype_getConstructorTerm(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer,
-                                                              jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  Term* retPointer = new Term(current->getConstructorTerm(cName));
-  env->ReleaseStringUTFChars(jName, s);
-  return ((jlong)retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    getName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Datatype_getName(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return env->NewStringUTF(current->getName().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    getNumConstructors
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Datatype_getNumConstructors(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jint)current->getNumConstructors();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isParametric
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isParametric(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isParametric();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isCodatatype
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isCodatatype(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isCodatatype();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isTuple
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isTuple(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isTuple();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isRecord
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isRecord(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isRecord();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isFinite
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isFinite(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isFinite();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isWellFounded
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isWellFounded(JNIEnv* env,
-                                                            jobject,
-                                                            jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isWellFounded();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    hasNestedRecursion
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_hasNestedRecursion(JNIEnv* env,
-                                                                 jobject,
-                                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->hasNestedRecursion();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Datatype_isNull(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return (jboolean)current->isNull();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Datatype
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Datatype_toString(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Datatype* current = (Datatype*)pointer;
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_DatatypeConstructor.cpp b/src/api/java/jni/cvc5_DatatypeConstructor.cpp
deleted file mode 100644 (file)
index 63aed36..0000000
+++ /dev/null
@@ -1,194 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_DatatypeConstructor.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL
-Java_cvc5_DatatypeConstructor_deletePointer(JNIEnv*, jclass, jlong pointer)
-{
-  delete ((DatatypeConstructor*)pointer);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_DatatypeConstructor_getName(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  return env->NewStringUTF(current->getName().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getConstructorTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_DatatypeConstructor_getConstructorTerm(
-    JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  Term* retPointer = new Term(current->getConstructorTerm());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getSpecializedConstructorTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_DatatypeConstructor_getSpecializedConstructorTerm(
-    JNIEnv* env, jobject, jlong pointer, jlong retSortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  Sort* sort = (Sort*)retSortPointer;
-  Term* retPointer = new Term(current->getSpecializedConstructorTerm(*sort));
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getTesterTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_DatatypeConstructor_getTesterTerm(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  Term* retPointer = new Term(current->getTesterTerm());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getNumSelectors
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_DatatypeConstructor_getNumSelectors(
-    JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  return (jint)current->getNumSelectors();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getSelector
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_DatatypeConstructor_getSelector__JI(
-    JNIEnv* env, jobject, jlong pointer, jint index)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  DatatypeSelector* retPointer =
-      new DatatypeSelector(current->operator[]((size_t)index));
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getSelector
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_DatatypeConstructor_getSelector__JLjava_lang_String_2(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer,
-                                                                jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  DatatypeSelector* retPointer =
-      new DatatypeSelector(current->operator[](cName));
-  env->ReleaseStringUTFChars(jName, s);
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    getSelectorTerm
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_DatatypeConstructor_getSelectorTerm(
-    JNIEnv* env, jobject, jlong pointer, jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  Term* retPointer = new Term(current->getSelectorTerm(cName));
-  env->ReleaseStringUTFChars(jName, s);
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_DatatypeConstructor_isNull(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  return (jboolean)current->isNull();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructor
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_DatatypeConstructor_toString(JNIEnv* env,
-                                                                 jobject,
-                                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_DatatypeConstructorDecl.cpp b/src/api/java/jni/cvc5_DatatypeConstructorDecl.cpp
deleted file mode 100644 (file)
index ce3c695..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_DatatypeConstructorDecl.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_DatatypeConstructorDecl
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL
-Java_cvc5_DatatypeConstructorDecl_deletePointer(JNIEnv*, jclass, jlong pointer)
-{
-  delete ((DatatypeConstructorDecl*)pointer);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructorDecl
- * Method:    addSelector
- * Signature: (JLjava/lang/String;J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_DatatypeConstructorDecl_addSelector(
-    JNIEnv* env, jobject, jlong pointer, jstring jName, jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  Sort* sort = (Sort*)sortPointer;
-  current->addSelector(cName, *sort);
-  env->ReleaseStringUTFChars(jName, s);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructorDecl
- * Method:    addSelectorSelf
- * Signature: (JLjava/lang/String;)V
- */
-JNIEXPORT void JNICALL Java_cvc5_DatatypeConstructorDecl_addSelectorSelf(
-    JNIEnv* env, jobject, jlong pointer, jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  current->addSelectorSelf(cName);
-  env->ReleaseStringUTFChars(jName, s);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructorDecl
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL
-Java_cvc5_DatatypeConstructorDecl_isNull(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
-  return (jboolean)current->isNull();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_DatatypeConstructorDecl
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL
-Java_cvc5_DatatypeConstructorDecl_toString(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_DatatypeDecl.cpp b/src/api/java/jni/cvc5_DatatypeDecl.cpp
deleted file mode 100644 (file)
index b68c378..0000000
+++ /dev/null
@@ -1,125 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_DatatypeDecl.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_DatatypeDecl_deletePointer(JNIEnv*,
-                                                            jclass,
-                                                            jlong pointer)
-{
-  delete ((DatatypeDecl*)pointer);
-}
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    addConstructor
- * Signature: (JJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_DatatypeDecl_addConstructor(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer,
-                                                             jlong declPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* current = (DatatypeDecl*)pointer;
-  DatatypeConstructorDecl* decl = (DatatypeConstructorDecl*)declPointer;
-  current->addConstructor(*decl);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    getNumConstructors
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_DatatypeDecl_getNumConstructors(JNIEnv* env,
-                                                                 jobject,
-                                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* current = (DatatypeDecl*)pointer;
-  return (jint)current->getNumConstructors();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    isParametric
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_DatatypeDecl_isParametric(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* current = (DatatypeDecl*)pointer;
-  return (jboolean)current->isParametric();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_DatatypeDecl_isNull(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* current = (DatatypeDecl*)pointer;
-  return (jboolean)current->isNull();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_DatatypeDecl_toString(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* current = (DatatypeDecl*)pointer;
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_DatatypeDecl
- * Method:    getName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_DatatypeDecl_getName(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* current = (DatatypeDecl*)pointer;
-  return env->NewStringUTF(current->getName().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_DatatypeSelector.cpp b/src/api/java/jni/cvc5_DatatypeSelector.cpp
deleted file mode 100644 (file)
index fee0b33..0000000
+++ /dev/null
@@ -1,125 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_DatatypeSelector.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_DatatypeSelector_deletePointer(JNIEnv*,
-                                                                jclass,
-                                                                jlong pointer)
-{
-  delete ((DatatypeSelector*)pointer);
-}
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    getName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_DatatypeSelector_getName(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeSelector* current = (DatatypeSelector*)pointer;
-  return env->NewStringUTF(current->getName().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    getSelectorTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_DatatypeSelector_getSelectorTerm(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeSelector* current = (DatatypeSelector*)pointer;
-  Term* retPointer = new Term(current->getSelectorTerm());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    getUpdaterTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_DatatypeSelector_getUpdaterTerm(JNIEnv* env,
-                                                                  jobject,
-                                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeSelector* current = (DatatypeSelector*)pointer;
-  Term* retPointer = new Term(current->getUpdaterTerm());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    getRangeSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_DatatypeSelector_getRangeSort(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeSelector* current = (DatatypeSelector*)pointer;
-  Sort* retPointer = new Sort(current->getRangeSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_DatatypeSelector_isNull(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeSelector* current = (DatatypeSelector*)pointer;
-  return (jboolean)current->isNull();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_DatatypeSelector
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_DatatypeSelector_toString(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeSelector* current = (DatatypeSelector*)pointer;
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_Grammar.cpp b/src/api/java/jni/cvc5_Grammar.cpp
deleted file mode 100644 (file)
index 1ca9ea7..0000000
+++ /dev/null
@@ -1,136 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Grammar.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Grammar
- * Method:    copyGrammar
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Grammar_copyGrammar(JNIEnv* env,
-                                                      jclass,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Grammar* current = reinterpret_cast<Grammar*>(pointer);
-  Grammar* retPointer = new Grammar(*current);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Grammar
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Grammar_deletePointer(JNIEnv*,
-                                                       jclass,
-                                                       jlong pointer)
-{
-  delete reinterpret_cast<Grammar*>(pointer);
-}
-
-/*
- * Class:     cvc5_Grammar
- * Method:    addRule
- * Signature: (JJJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Grammar_addRule(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer,
-                                                 jlong ntSymbolPointer,
-                                                 jlong rulePointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Grammar* current = reinterpret_cast<Grammar*>(pointer);
-  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
-  Term* rule = reinterpret_cast<Term*>(rulePointer);
-  current->addRule(*ntSymbol, *rule);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Grammar
- * Method:    addRules
- * Signature: (JJ[J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Grammar_addRules(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer,
-                                                  jlong ntSymbolPointer,
-                                                  jlongArray rulePointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Grammar* current = reinterpret_cast<Grammar*>(pointer);
-  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
-  std::vector<Term> rules = getObjectsFromPointers<Term>(env, rulePointers);
-  current->addRules(*ntSymbol, rules);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Grammar
- * Method:    addAnyConstant
- * Signature: (JJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Grammar_addAnyConstant(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jlong ntSymbolPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Grammar* current = reinterpret_cast<Grammar*>(pointer);
-  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
-  current->addAnyConstant(*ntSymbol);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Grammar
- * Method:    addAnyVariable
- * Signature: (JJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Grammar_addAnyVariable(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jlong ntSymbolPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Grammar* current = reinterpret_cast<Grammar*>(pointer);
-  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
-  current->addAnyVariable(*ntSymbol);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Grammar
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Grammar_toString(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Grammar* current = reinterpret_cast<Grammar*>(pointer);
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_Op.cpp b/src/api/java/jni/cvc5_Op.cpp
deleted file mode 100644 (file)
index 5c2a006..0000000
+++ /dev/null
@@ -1,200 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Op.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Op
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Op_deletePointer(JNIEnv*,
-                                                  jclass,
-                                                  jlong pointer)
-{
-  delete reinterpret_cast<Op*>(pointer);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    equals
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Op_equals(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer1,
-                                               jlong pointer2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* op1 = reinterpret_cast<Op*>(pointer1);
-  Op* op2 = reinterpret_cast<Op*>(pointer2);
-  // We compare the actual operators, not their pointers.
-  return static_cast<jboolean>(*op1 == *op2);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    getKind
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Op_getKind(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  return static_cast<jboolean>(current->getKind());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Op_isNull(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  return static_cast<jboolean>(current->isNull());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    isIndexed
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Op_isIndexed(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  return static_cast<jboolean>(current->isIndexed());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, false);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    getNumIndices
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Op_getNumIndices(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  return static_cast<jint>(current->getNumIndices());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    getIntegerIndices
- * Signature: (J)[I
- */
-JNIEXPORT jintArray JNICALL Java_cvc5_Op_getIntegerIndices(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  size_t size = current->getNumIndices();
-  std::vector<jint> indices(size);
-  if (size == 1)
-  {
-    uint32_t index = current->getIndices<uint32_t>();
-    indices[0] = index;
-  }
-
-  if (size == 2)
-  {
-    std::pair<uint32_t, uint32_t> pair =
-        current->getIndices<std::pair<uint32_t, uint32_t>>();
-    indices[0] = pair.first;
-    indices[1] = pair.second;
-  }
-
-  if (size > 2)
-  {
-    std::string message = "Unhandled case when number of indices > 2.";
-    throw CVC5ApiException(message);
-  }
-
-  jintArray ret = env->NewIntArray((jsize)size);
-  env->SetIntArrayRegion(ret, 0, size, indices.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    getStringIndices
- * Signature: (J)[Ljava/lang/String;
- */
-JNIEXPORT jobjectArray JNICALL Java_cvc5_Op_getStringIndices(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  size_t size = current->getNumIndices();
-  std::vector<jstring> indices(size);
-  if (size == 1)
-  {
-    std::string cIndex = current->getIndices<std::string>();
-    jstring jIndex = env->NewStringUTF(cIndex.c_str());
-    indices[0] = jIndex;
-  }
-
-  if (size > 1)  // currently only one string is implemented in cvc5.cpp
-  {
-    std::string message = "Unhandled case when number of indices > 1.";
-    throw CVC5ApiException(message);
-  }
-
-  // construct a java array of String
-  jclass stringClass = env->FindClass("Ljava/lang/String;");
-  jobjectArray ret = env->NewObjectArray((jsize)size, stringClass, nullptr);
-  for (size_t i = 0; i < size; i++)
-  {
-    env->SetObjectArrayElement(ret, i, indices[i]);
-  }
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Op
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Op_toString(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* current = reinterpret_cast<Op*>(pointer);
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_OptionInfo.cpp b/src/api/java/jni/cvc5_OptionInfo.cpp
deleted file mode 100644 (file)
index c4bcc2e..0000000
+++ /dev/null
@@ -1,351 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_OptionInfo.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_OptionInfo_deletePointer(JNIEnv*,
-                                                          jclass,
-                                                          jlong pointer)
-{
-  delete reinterpret_cast<OptionInfo*>(pointer);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_OptionInfo_toString(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  std::stringstream ss;
-  ss << *current;
-  return env->NewStringUTF(ss.str().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    getName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_OptionInfo_getName(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  return env->NewStringUTF(current->name.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    getAliases
- * Signature: (J)[Ljava/lang/String;
- */
-JNIEXPORT jobjectArray JNICALL Java_cvc5_OptionInfo_getAliases(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  jobjectArray ret = getStringArrayFromStringVector(env, current->aliases);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    getSetByUser
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_OptionInfo_getSetByUser(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  return static_cast<jboolean>(current->setByUser);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/**
- * Convert OptionInfo::NumberInfo cpp object to OptionInfo.NumberInfo java
- * object
- * @tparam T cpp integer types int64_t, uint64_t, etc
- * @param env jni environment
- * @param optionInfo a java object for this OptionInfo
- * @param numberInfoClass the java class for OptionInfo.NumberInfo
- * @param methodId a constructor for OptionInfo.NumberInfo
- * @param info the cpp OptionInfo::NumberInfo object
- * @return a java object of class OptionInfo.NumberInfo<BigInteger>
- */
-template <typename T>
-jobject getNumberInfoFromInteger(JNIEnv* env,
-                                 const _jobject* optionInfo,
-                                 jclass numberInfoClass,
-                                 jmethodID methodId,
-                                 const OptionInfo::NumberInfo<T>& info)
-{
-  jobject defaultValue = getBigIntegerObject<T>(env, info.defaultValue);
-  jobject currentValue = getBigIntegerObject<T>(env, info.currentValue);
-  jobject minimum = nullptr;
-  if (info.minimum)
-  {
-    minimum = getBigIntegerObject<T>(env, *info.minimum);
-  }
-  jobject maximum = nullptr;
-  if (info.maximum)
-  {
-    maximum = getBigIntegerObject<T>(env, *info.maximum);
-  }
-  jobject ret = env->NewObject(numberInfoClass,
-                               methodId,
-                               optionInfo,
-                               defaultValue,
-                               currentValue,
-                               minimum,
-                               maximum);
-
-  return ret;
-}
-
-template <typename T>
-jobject getNumberInfoFromInteger(JNIEnv* env,
-                                 const _jobject* optionInfo,
-                                 jclass numberInfoClass,
-                                 jmethodID methodId,
-                                 const OptionInfo::NumberInfo<int64_t>& info);
-
-template <typename T>
-jobject getNumberInfoFromInteger(JNIEnv* env,
-                                 const _jobject* optionInfo,
-                                 jclass numberInfoClass,
-                                 jmethodID methodId,
-                                 const OptionInfo::NumberInfo<uint64_t>& info);
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    getBaseInfo
- * Signature: (J)Lcvc5/BaseInfo;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_OptionInfo_getBaseInfo(JNIEnv* env,
-                                                           jobject optionInfo,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  std::variant<OptionInfo::VoidInfo,
-               OptionInfo::ValueInfo<bool>,
-               OptionInfo::ValueInfo<std::string>,
-               OptionInfo::NumberInfo<int64_t>,
-               OptionInfo::NumberInfo<uint64_t>,
-               OptionInfo::NumberInfo<double>,
-               OptionInfo::ModeInfo>
-      v = current->valueInfo;
-
-  if (std::holds_alternative<OptionInfo::VoidInfo>(v))
-  {
-    jclass voidInfoClass = env->FindClass("cvc5/OptionInfo$VoidInfo");
-    jmethodID methodId =
-        env->GetMethodID(voidInfoClass, "<init>", "(Lcvc5/OptionInfo;)V");
-    jobject ret = env->NewObject(voidInfoClass, methodId, optionInfo);
-    return ret;
-  }
-
-  if (std::holds_alternative<OptionInfo::ValueInfo<bool>>(v)
-      || std::holds_alternative<OptionInfo::ValueInfo<std::string>>(v))
-  {
-    jclass valueInfoClass = env->FindClass("cvc5/OptionInfo$ValueInfo");
-    jmethodID methodId = env->GetMethodID(
-        valueInfoClass,
-        "<init>",
-        "(Lcvc5/OptionInfo;Ljava/lang/Object;Ljava/lang/Object;)V");
-
-    if (std::holds_alternative<OptionInfo::ValueInfo<bool>>(v))
-    {
-      auto info = std::get<OptionInfo::ValueInfo<bool>>(v);
-      jobject currentValue = getBooleanObject(env, info.currentValue);
-      jobject defaultValue = getBooleanObject(env, info.defaultValue);
-      jobject ret = env->NewObject(
-          valueInfoClass, methodId, optionInfo, defaultValue, currentValue);
-      return ret;
-    }
-
-    if (std::holds_alternative<OptionInfo::ValueInfo<std::string>>(v))
-    {
-      auto info = std::get<OptionInfo::ValueInfo<std::string>>(v);
-      jstring defaultValue = env->NewStringUTF(info.defaultValue.c_str());
-      jstring currentValue = env->NewStringUTF(info.currentValue.c_str());
-      jobject ret = env->NewObject(
-          valueInfoClass, methodId, optionInfo, defaultValue, currentValue);
-      return ret;
-    }
-  }
-
-  if (std::holds_alternative<OptionInfo::NumberInfo<int64_t>>(v)
-      || std::holds_alternative<OptionInfo::NumberInfo<uint64_t>>(v)
-      || std::holds_alternative<OptionInfo::NumberInfo<double>>(v))
-  {
-    jclass numberInfoClass = env->FindClass("cvc5/OptionInfo$NumberInfo");
-    jmethodID methodId =
-        env->GetMethodID(numberInfoClass,
-                         "<init>",
-                         "(Lcvc5/OptionInfo;Ljava/lang/Object;Ljava/lang/"
-                         "Object;Ljava/lang/Object;Ljava/lang/Object;)V");
-
-    if (std::holds_alternative<OptionInfo::NumberInfo<int64_t>>(v))
-    {
-      auto info = std::get<OptionInfo::NumberInfo<int64_t>>(v);
-      return getNumberInfoFromInteger(
-          env, optionInfo, numberInfoClass, methodId, info);
-    }
-
-    if (std::holds_alternative<OptionInfo::NumberInfo<uint64_t>>(v))
-    {
-      auto info = std::get<OptionInfo::NumberInfo<uint64_t>>(v);
-      return getNumberInfoFromInteger(
-          env, optionInfo, numberInfoClass, methodId, info);
-    }
-
-    if (std::holds_alternative<OptionInfo::NumberInfo<double>>(v))
-    {
-      auto info = std::get<OptionInfo::NumberInfo<double>>(v);
-      jobject defaultValue = getDoubleObject(env, info.defaultValue);
-      jobject currentValue = getDoubleObject(env, info.currentValue);
-      jobject minimum = nullptr;
-      if (info.minimum)
-      {
-        minimum = getDoubleObject(env, *info.minimum);
-      }
-      jobject maximum = nullptr;
-      if (info.maximum)
-      {
-        maximum = getDoubleObject(env, *info.maximum);
-      }
-      jobject ret = env->NewObject(numberInfoClass,
-                                   methodId,
-                                   optionInfo,
-                                   defaultValue,
-                                   currentValue,
-                                   minimum,
-                                   maximum);
-      return ret;
-    }
-  }
-
-  if (std::holds_alternative<OptionInfo::ModeInfo>(v))
-  {
-    jclass modeInfoClass = env->FindClass("cvc5/OptionInfo$ModeInfo");
-    jmethodID methodId =
-        env->GetMethodID(modeInfoClass,
-                         "<init>",
-                         "(Lcvc5/OptionInfo;Ljava/lang/String;Ljava/lang/"
-                         "String;[Ljava/lang/String;)V");
-
-    auto info = std::get<OptionInfo::ModeInfo>(v);
-    jstring defaultValue = env->NewStringUTF(info.defaultValue.c_str());
-    jstring currentValue = env->NewStringUTF(info.currentValue.c_str());
-    jobject stringArray = getStringArrayFromStringVector(env, info.modes);
-    jobject ret = env->NewObject(modeInfoClass,
-                                 methodId,
-                                 optionInfo,
-                                 defaultValue,
-                                 currentValue,
-                                 stringArray);
-    return ret;
-  }
-
-  return nullptr;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    booleanValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_OptionInfo_booleanValue(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  return static_cast<jboolean>(current->boolValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    stringValue
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_OptionInfo_stringValue(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  std::string ret = current->stringValue();
-  return env->NewStringUTF(ret.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    intValue
- * Signature: (J)Ljava/math/BigInteger;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_OptionInfo_intValue(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  std::int64_t value = current->intValue();
-  jobject ret = getBigIntegerObject<std::int64_t>(env, value);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_OptionInfo
- * Method:    doubleValue
- * Signature: (J)D
- */
-JNIEXPORT jdouble JNICALL Java_cvc5_OptionInfo_doubleValue(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
-  double ret = current->doubleValue();
-  return static_cast<jdouble>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jdouble>(0.0));
-}
diff --git a/src/api/java/jni/cvc5_Result.cpp b/src/api/java/jni/cvc5_Result.cpp
deleted file mode 100644 (file)
index 4bc5cec..0000000
+++ /dev/null
@@ -1,186 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Result.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Result
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Result_deletePointer(JNIEnv*,
-                                                      jclass,
-                                                      jlong pointer)
-{
-  delete ((Result*)pointer);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isNull(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isNull();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isSat
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isSat(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isSat();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isUnsat
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isUnsat(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isUnsat();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isSatUnknown
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isSatUnknown(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isSatUnknown();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isEntailed
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isEntailed(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isEntailed();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isNotEntailed
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isNotEntailed(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isNotEntailed();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    isEntailmentUnknown
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_isEntailmentUnknown(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jboolean)current->isEntailmentUnknown();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    equals
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Result_equals(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer1,
-                                                   jlong pointer2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* result1 = (Result*)pointer1;
-  Result* result2 = (Result*)pointer2;
-  // We compare the actual terms, not their pointers.
-  return (jboolean)(*result1 == *result2);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    getUnknownExplanation
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Result_getUnknownExplanation(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return (jint)current->getUnknownExplanation();
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Result
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Result_toString(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* current = (Result*)pointer;
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_Solver.cpp b/src/api/java/jni/cvc5_Solver.cpp
deleted file mode 100644 (file)
index cdbb48d..0000000
+++ /dev/null
@@ -1,2751 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Solver.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Solver
- * Method:    newSolver
- * Signature: ()J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_newSolver(JNIEnv*, jobject)
-{
-  Solver* solver = new Solver();
-  return reinterpret_cast<jlong>(solver);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_deletePointer(JNIEnv*,
-                                                      jclass,
-                                                      jlong pointer)
-{
-  delete (reinterpret_cast<Solver*>(pointer));
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getNullSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getNullSort(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getNullSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getBooleanSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getBooleanSort(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getBooleanSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getIntegerSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getIntegerSort(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getIntegerSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getRealSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getRealSort(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getRealSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getRegExpSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getRegExpSort(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getRegExpSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getRoundingModeSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getRoundingModeSort(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getRoundingModeSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getStringSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getStringSort(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->getStringSort());
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkArraySort
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkArraySort(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jlong indexSortPointer,
-                                                     jlong elementSortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* indexSort = reinterpret_cast<Sort*>(indexSortPointer);
-  Sort* elementSort = reinterpret_cast<Sort*>(elementSortPointer);
-  Sort* retPointer = new Sort(solver->mkArraySort(*indexSort, *elementSort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkBitVectorSort
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkBitVectorSort(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer,
-                                                         jint size)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer = new Sort(solver->mkBitVectorSort((uint32_t)size));
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkFloatingPointSort
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkFloatingPointSort(
-    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sortPointer =
-      new Sort(solver->mkFloatingPointSort((uint32_t)exp, (uint32_t)sig));
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeSort
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkDatatypeSort(
-    JNIEnv* env, jobject, jlong pointer, jlong datatypeDeclPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  DatatypeDecl* decl = reinterpret_cast<DatatypeDecl*>(datatypeDeclPointer);
-  Sort* retPointer = new Sort(solver->mkDatatypeSort(*decl));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeSorts
- * Signature: (J[J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_mkDatatypeSorts__J_3J(
-    JNIEnv* env, jobject, jlong pointer, jlongArray jDecls)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<DatatypeDecl> decls =
-      getObjectsFromPointers<DatatypeDecl>(env, jDecls);
-  std::vector<Sort> sorts = solver->mkDatatypeSorts(decls);
-  std::vector<jlong> sortPointers(sorts.size());
-
-  for (size_t i = 0; i < sorts.size(); i++)
-  {
-    sortPointers[i] = reinterpret_cast<jlong>(new Sort(sorts[i]));
-  }
-
-  jlongArray ret = env->NewLongArray(sorts.size());
-  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeSorts
- * Signature: (J[J[J)[J
- */
-JNIEXPORT jlongArray JNICALL
-Java_cvc5_Solver_mkDatatypeSorts__J_3J_3J(JNIEnv* env,
-                                          jobject,
-                                          jlong pointer,
-                                          jlongArray jDecls,
-                                          jlongArray jUnresolved)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<DatatypeDecl> decls =
-      getObjectsFromPointers<DatatypeDecl>(env, jDecls);
-  std::vector<Sort> cUnresolved =
-      getObjectsFromPointers<Sort>(env, jUnresolved);
-  std::set<Sort> unresolved(cUnresolved.begin(), cUnresolved.end());
-  std::vector<Sort> sorts = solver->mkDatatypeSorts(decls, unresolved);
-  jlongArray ret = getPointersFromObjects<Sort>(env, sorts);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkFunctionSort
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkFunctionSort__JJJ(JNIEnv* env,
-                                     jobject,
-                                     jlong pointer,
-                                     jlong domainPointer,
-                                     jlong codomainPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* domain = reinterpret_cast<Sort*>(domainPointer);
-  Sort* codomain = reinterpret_cast<Sort*>(codomainPointer);
-  Sort* sortPointer = new Sort(solver->mkFunctionSort(*domain, *codomain));
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkFunctionSort
- * Signature: (J[JJ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkFunctionSort__J_3JJ(JNIEnv* env,
-                                       jobject,
-                                       jlong pointer,
-                                       jlongArray sortPointers,
-                                       jlong codomainPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* codomain = reinterpret_cast<Sort*>(codomainPointer);
-  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
-  Sort* retPointer = new Sort(solver->mkFunctionSort(sorts, *codomain));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkParamSort
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkParamSort(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jstring jSymbol)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  Sort* retPointer = new Sort(solver->mkParamSort(cSymbol));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkPredicateSort
- * Signature: (J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkPredicateSort(
-    JNIEnv* env, jobject, jlong pointer, jlongArray sortPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
-  Sort* retPointer = new Sort(solver->mkPredicateSort(sorts));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkRecordSort
- * Signature: (J[Lcvc5/Pair;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkRecordSort(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jobjectArray jFields)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  jsize size = env->GetArrayLength(jFields);
-  // Lcvc5/Pair; is signature of cvc5.Pair<String, Long>
-  jclass pairClass = env->FindClass("Lcvc5/Pair;");
-  jclass longClass = env->FindClass("Ljava/lang/Long;");
-  // Ljava/lang/Object; is the signature of cvc5.Pair.first field
-  jfieldID firstFieldId =
-      env->GetFieldID(pairClass, "first", "Ljava/lang/Object;");
-  // Ljava/lang/Object; is the signature of cvc5.Pair.second field
-  jfieldID secondFieldId =
-      env->GetFieldID(pairClass, "second", "Ljava/lang/Object;");
-  // we need to call method longValue to get long Long object
-  jmethodID methodId = env->GetMethodID(longClass, "longValue", "()J");
-
-  std::vector<std::pair<std::string, Sort>> cFields;
-  for (jsize i = 0; i < size; i++)
-  {
-    // get the pair at index i
-    jobject object = env->GetObjectArrayElement(jFields, i);
-
-    // get the object at cvc5.Pair.first and convert it to char *
-    jstring jFirst = (jstring)env->GetObjectField(object, firstFieldId);
-    const char* cFirst = env->GetStringUTFChars(jFirst, nullptr);
-
-    // get the object at cvc5.Pair.second and convert it to Sort
-    jobject jSecond = env->GetObjectField(object, secondFieldId);
-    jlong sortPointer = env->CallLongMethod(jSecond, methodId);
-    Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-
-    // add the pair to to the list of fields
-    cFields.push_back(std::make_pair(std::string(cFirst), *sort));
-  }
-  // get the record sort from the solver
-  Sort* retPointer = new Sort(solver->mkRecordSort(cFields));
-  // return a pointer to the sort
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSetSort
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSetSort(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer,
-                                                   jlong elemSortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* elemSort = reinterpret_cast<Sort*>(elemSortPointer);
-  Sort* retPointer = new Sort(solver->mkSetSort(*elemSort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkBagSort
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkBagSort(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer,
-                                                   jlong elemSortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* elemSort = reinterpret_cast<Sort*>(elemSortPointer);
-  Sort* retPointer = new Sort(solver->mkBagSort(*elemSort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSequenceSort
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSequenceSort(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jlong elemSortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* elemSort = reinterpret_cast<Sort*>(elemSortPointer);
-  Sort* sortPointer = new Sort(solver->mkSequenceSort(*elemSort));
-  return reinterpret_cast<jlong>(sortPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkUninterpretedSort
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkUninterpretedSort(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer,
-                                                             jstring jSymbol)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* cSymbol = env->GetStringUTFChars(jSymbol, nullptr);
-  Sort* sort = new Sort(solver->mkUninterpretedSort(std::string(cSymbol)));
-  env->ReleaseStringUTFChars(jSymbol, cSymbol);
-  return reinterpret_cast<jlong>(sort);
-
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSortConstructorSort
- * Signature: (JLjava/lang/String;I)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSortConstructorSort(
-    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jint arity)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  Sort* retPointer =
-      new Sort(solver->mkSortConstructorSort(cSymbol, (size_t)arity));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTupleSort
- * Signature: (J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTupleSort(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jlongArray sortPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
-  Sort* retPointer = new Sort(solver->mkTupleSort(sorts));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JI(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jint kindValue)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Term* retPointer = new Term(solver->mkTerm(kind));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JIJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JIJ(
-    JNIEnv* env, jobject, jlong pointer, jint kindValue, jlong childPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Term* child = reinterpret_cast<Term*>(childPointer);
-  Term* termPointer = new Term(solver->mkTerm(kind, *child));
-  return reinterpret_cast<jlong>(termPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JIJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JIJJ(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jint kindValue,
-                                                      jlong child1Pointer,
-                                                      jlong child2Pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
-  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
-  Term* termPointer = new Term(solver->mkTerm(kind, *child1, *child2));
-  return reinterpret_cast<jlong>(termPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JIJJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JIJJJ(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jint kindValue,
-                                                       jlong child1Pointer,
-                                                       jlong child2Pointer,
-                                                       jlong child3Pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
-  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
-  Term* child3 = reinterpret_cast<Term*>(child3Pointer);
-  Term* retPointer = new Term(solver->mkTerm(kind, *child1, *child2, *child3));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JI[J)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkTerm__JI_3J(JNIEnv* env,
-                               jobject,
-                               jlong pointer,
-                               jint kindValue,
-                               jlongArray childrenPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  std::vector<Term> children =
-      getObjectsFromPointers<Term>(env, childrenPointers);
-  Term* retPointer = new Term(solver->mkTerm(kind, children));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JJ(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jlong opPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Op* op = reinterpret_cast<Op*>(opPointer);
-  Term* retPointer = new Term(solver->mkTerm(*op));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JJJ(
-    JNIEnv* env, jobject, jlong pointer, jlong opPointer, jlong childPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Op* op = reinterpret_cast<Op*>(opPointer);
-  Term* child = reinterpret_cast<Term*>(childPointer);
-  Term* retPointer = new Term(solver->mkTerm(*op, *child));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JJJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JJJJ(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jlong opPointer,
-                                                      jlong child1Pointer,
-                                                      jlong child2Pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Op* op = reinterpret_cast<Op*>(opPointer);
-  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
-  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
-  Term* retPointer = new Term(solver->mkTerm(*op, *child1, *child2));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JJJJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTerm__JJJJJ(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong opPointer,
-                                                       jlong child1Pointer,
-                                                       jlong child2Pointer,
-                                                       jlong child3Pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Op* op = reinterpret_cast<Op*>(opPointer);
-  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
-  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
-  Term* child3 = reinterpret_cast<Term*>(child3Pointer);
-  Term* retPointer = new Term(solver->mkTerm(*op, *child1, *child2, *child3));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTerm
- * Signature: (JJ[J)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkTerm__JJ_3J(JNIEnv* env,
-                               jobject,
-                               jlong pointer,
-                               jlong opPointer,
-                               jlongArray childrenPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Op* op = reinterpret_cast<Op*>(opPointer);
-  std::vector<Term> children =
-      getObjectsFromPointers<Term>(env, childrenPointers);
-  Term* retPointer = new Term(solver->mkTerm(*op, children));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTuple
- * Signature: (J[J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTuple(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer,
-                                                 jlongArray sortPointers,
-                                                 jlongArray termPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
-  std::vector<Term> terms = getObjectsFromPointers<Term>(env, termPointers);
-  Term* retPointer = new Term(solver->mkTuple(sorts, terms));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkOp
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkOp__JI(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer,
-                                                  jint kindValue)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Op* retPointer = new Op(solver->mkOp(kind));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkOp
- * Signature: (JILjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkOp__JILjava_lang_String_2(
-    JNIEnv* env, jobject, jlong pointer, jint kindValue, jstring jArg)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  const char* s = env->GetStringUTFChars(jArg, nullptr);
-  std::string cArg(s);
-
-  Op* retPointer = new Op(solver->mkOp(kind, cArg));
-
-  env->ReleaseStringUTFChars(jArg, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkOp
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkOp__JII(
-    JNIEnv* env, jobject, jlong pointer, jint kindValue, jint arg)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Op* retPointer = new Op(solver->mkOp(kind, (uint32_t)arg));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkOp
- * Signature: (JIII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkOp__JIII(
-    JNIEnv* env, jobject, jlong pointer, jint kindValue, jint arg1, jint arg2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-  Op* retPointer = new Op(solver->mkOp(kind, (uint32_t)arg1, (uint32_t)arg2));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkOp
- * Signature: (JI[I)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkOp__JI_3I(
-    JNIEnv* env, jobject, jlong pointer, jint kindValue, jintArray jArgs)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Kind kind = (Kind)kindValue;
-
-  jsize size = env->GetArrayLength(jArgs);
-  jint* argElements = env->GetIntArrayElements(jArgs, nullptr);
-
-  std::vector<uint32_t> cArgs(size);
-  for (jsize i = 0; i < size; i++)
-  {
-    cArgs[i] = (uint32_t)argElements[i];
-  }
-  env->ReleaseIntArrayElements(jArgs, argElements, 0);
-
-  Op* retPointer = new Op(solver->mkOp(kind, cArgs));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkTrue
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkTrue(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* termPointer = new Term(solver->mkTrue());
-  return reinterpret_cast<jlong>(termPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkFalse
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkFalse(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* termPointer = new Term(solver->mkFalse());
-  return reinterpret_cast<jlong>(termPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkBoolean
- * Signature: (JZ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkBoolean(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer,
-                                                   jboolean val)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkBoolean((bool)val));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkPi
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkPi(JNIEnv* env,
-                                              jobject,
-                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkPi());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkInteger
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkInteger__JLjava_lang_String_2(
-    JNIEnv* env, jobject, jlong pointer, jstring jS)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jS, nullptr);
-  std::string cS(s);
-  Term* retPointer = new Term(solver->mkInteger(cS));
-  env->ReleaseStringUTFChars(jS, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkInteger
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkInteger__JJ(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong val)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* termPointer = new Term(solver->mkInteger((int64_t)val));
-  return reinterpret_cast<jlong>(termPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkReal
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkReal__JLjava_lang_String_2(
-    JNIEnv* env, jobject, jlong pointer, jstring jS)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jS, nullptr);
-  std::string cS(s);
-  Term* retPointer = new Term(solver->mkReal(cS));
-  env->ReleaseStringUTFChars(jS, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkRealValue
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkRealValue(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jlong val)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkReal((int64_t)val));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkReal
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkReal__JJJ(
-    JNIEnv* env, jobject, jlong pointer, jlong num, jlong den)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkReal((int64_t)num, (int64_t)den));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkRegexpEmpty
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkRegexpEmpty(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkRegexpEmpty());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkRegexpSigma
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkRegexpSigma(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkRegexpSigma());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkEmptySet
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkEmptySet(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->mkEmptySet(*sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkEmptyBag
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkEmptyBag(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->mkEmptyBag(*sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSepEmp
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSepEmp(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkSepEmp());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSepNil
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSepNil(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer,
-                                                  jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->mkSepNil(*sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkString
- * Signature: (JLjava/lang/String;Z)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkString__JLjava_lang_String_2Z(
-    JNIEnv* env, jobject, jlong pointer, jstring jS, jboolean useEscSequences)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jS, nullptr);
-  std::string cS(s);
-  Term* retPointer = new Term(solver->mkString(cS, (bool)useEscSequences));
-  env->ReleaseStringUTFChars(jS, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkEmptySequence
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkEmptySequence(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer,
-                                                         jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->mkEmptySequence(*sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkUniverseSet
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkUniverseSet(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->mkUniverseSet(*sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkBitVector
- * Signature: (JIJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkBitVector__JIJ(
-    JNIEnv* env, jobject, jlong pointer, jint size, jlong val)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer =
-      new Term(solver->mkBitVector((uint32_t)size, (uint64_t)val));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkBitVector
- * Signature: (JILjava/lang/String;I)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkBitVector__JILjava_lang_String_2I(
-    JNIEnv* env, jobject, jlong pointer, jint size, jstring jS, jint base)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jS, nullptr);
-  std::string cS(s);
-  Term* retPointer =
-      new Term(solver->mkBitVector((uint32_t)size, cS, (uint32_t)base));
-  env->ReleaseStringUTFChars(jS, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkConstArray
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkConstArray(
-    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jlong valPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* val = reinterpret_cast<Term*>(valPointer);
-  Term* retPointer = new Term(solver->mkConstArray(*sort, *val));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkPosInf
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkPosInf(
-    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkPosInf((uint32_t)exp, (uint32_t)sig));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkNegInf
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkNegInf(
-    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkNegInf((uint32_t)exp, (uint32_t)sig));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkNaN
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkNaN(JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkNaN((uint32_t)exp, (uint32_t)sig));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkPosZero
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkPosZero(
-    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkPosZero((uint32_t)exp, (uint32_t)sig));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkNegZero
- * Signature: (JII)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkNegZero(
-    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkNegZero((uint32_t)exp, (uint32_t)sig));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkRoundingMode
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkRoundingMode(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jint rm)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkRoundingMode((RoundingMode)rm));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkUninterpretedConst
- * Signature: (JJI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkUninterpretedConst(
-    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jint index)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer =
-      new Term(solver->mkUninterpretedConst(*sort, (int32_t)index));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkAbstractValue
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkAbstractValue__JLjava_lang_String_2(
-    JNIEnv* env, jobject, jlong pointer, jstring jIndex)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jIndex, nullptr);
-  std::string cIndex(s);
-  Term* retPointer = new Term(solver->mkAbstractValue(cIndex));
-  env->ReleaseStringUTFChars(jIndex, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkAbstractValue
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkAbstractValue__JJ(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer,
-                                                             jlong index)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->mkAbstractValue((uint64_t)index));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkFloatingPoint
- * Signature: (JIIJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkFloatingPoint(
-    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig, jlong valPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* val = reinterpret_cast<Term*>(valPointer);
-  Term* retPointer =
-      new Term(solver->mkFloatingPoint((uint32_t)exp, (uint32_t)sig, *val));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkConst
- * Signature: (JJLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkConst__JJLjava_lang_String_2(
-    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jstring jSymbol)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  Term* retPointer = new Term(solver->mkConst(*sort, cSymbol));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkConst
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkConst__JJ(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->mkConst(*sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkVar
- * Signature: (JJLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkVar(
-    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jstring jSymbol)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  Term* ret = new Term(solver->mkVar(*sort, cSymbol));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeConstructorDecl
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkDatatypeConstructorDecl(
-    JNIEnv* env, jobject, jlong pointer, jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-
-  DatatypeConstructorDecl* retPointer =
-      new DatatypeConstructorDecl(solver->mkDatatypeConstructorDecl(cName));
-  env->ReleaseStringUTFChars(jName, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeDecl
- * Signature: (JLjava/lang/String;Z)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkDatatypeDecl__JLjava_lang_String_2Z(
-    JNIEnv* env, jobject, jlong pointer, jstring jName, jboolean isCoDatatype)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  DatatypeDecl* retPointer =
-      new DatatypeDecl(solver->mkDatatypeDecl(cName, (bool)isCoDatatype));
-  env->ReleaseStringUTFChars(jName, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeDecl
- * Signature: (JLjava/lang/String;JZ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkDatatypeDecl__JLjava_lang_String_2JZ(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jstring jName,
-                                                        jlong paramPointer,
-                                                        jboolean isCoDatatype)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  Sort* param = reinterpret_cast<Sort*>(paramPointer);
-  DatatypeDecl* retPointer = new DatatypeDecl(
-      solver->mkDatatypeDecl(cName, *param, (bool)isCoDatatype));
-  env->ReleaseStringUTFChars(jName, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkDatatypeDecl
- * Signature: (JLjava/lang/String;[JZ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_mkDatatypeDecl__JLjava_lang_String_2_3JZ(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer,
-                                                          jstring jName,
-                                                          jlongArray jParams,
-                                                          jboolean isCoDatatype)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  std::vector<Sort> params = getObjectsFromPointers<Sort>(env, jParams);
-  DatatypeDecl* retPointer = new DatatypeDecl(
-      solver->mkDatatypeDecl(cName, params, (bool)isCoDatatype));
-  env->ReleaseStringUTFChars(jName, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    simplify
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_simplify(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer,
-                                                  jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* retPointer = new Term(solver->simplify(*term));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    assertFormula
- * Signature: (JJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_assertFormula(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  solver->assertFormula(*term);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    checkSat
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_checkSat(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Result* retPointer = new Result(solver->checkSat());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    checkSatAssuming
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_checkSatAssuming__JJ(
-    JNIEnv* env, jobject, jlong pointer, jlong assumptionPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* assumption = reinterpret_cast<Term*>(assumptionPointer);
-  Result* retPointer = new Result(solver->checkSatAssuming(*assumption));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    checkSatAssuming
- * Signature: (J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_checkSatAssuming__J_3J(
-    JNIEnv* env, jobject, jlong pointer, jlongArray jAssumptions)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> assumptions =
-      getObjectsFromPointers<Term>(env, jAssumptions);
-  Result* retPointer = new Result(solver->checkSatAssuming(assumptions));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    checkEntailed
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_checkEntailed__JJ(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer,
-                                                           jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Result* retPointer = new Result(solver->checkEntailed(*term));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    checkEntailed
- * Signature: (J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_checkEntailed__J_3J(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer,
-                                                             jlongArray jTerms)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
-  Result* retPointer = new Result(solver->checkEntailed(terms));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    declareDatatype
- * Signature: (JLjava/lang/String;[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_declareDatatype(
-    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jlongArray jCtors)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<DatatypeConstructorDecl> ctors =
-      getObjectsFromPointers<DatatypeConstructorDecl>(env, jCtors);
-  Sort* retPointer = new Sort(solver->declareDatatype(cSymbol, ctors));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    declareFun
- * Signature: (JLjava/lang/String;[JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_declareFun(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jstring jSymbol,
-                                                    jlongArray jSorts,
-                                                    jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, jSorts);
-  Term* retPointer = new Term(solver->declareFun(cSymbol, sorts, *sort));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    declareSort
- * Signature: (JLjava/lang/String;I)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_declareSort(
-    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jint arity)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  Sort* retPointer = new Sort(solver->declareSort(cSymbol, (uint32_t)arity));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    defineFun
- * Signature: (JLjava/lang/String;[JJJZ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_defineFun__JLjava_lang_String_2_3JJJZ(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jstring jSymbol,
-                                                       jlongArray jVars,
-                                                       jlong sortPointer,
-                                                       jlong termPointer,
-                                                       jboolean global)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer =
-      new Term(solver->defineFun(cSymbol, vars, *sort, *term, (bool)global));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    defineFun
- * Signature: (JJ[JJZ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_defineFun__JJ_3JJZ(JNIEnv* env,
-                                                            jobject,
-                                                            jlong pointer,
-                                                            jlong funPointer,
-                                                            jlongArray jVars,
-                                                            jlong termPointer,
-                                                            jboolean global)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* fun = reinterpret_cast<Term*>(funPointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer =
-      new Term(solver->defineFun(*fun, vars, *term, (bool)global));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    defineFunRec
- * Signature: (JLjava/lang/String;[JJJZ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_defineFunRec__JLjava_lang_String_2_3JJJZ(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer,
-                                                          jstring jSymbol,
-                                                          jlongArray jVars,
-                                                          jlong sortPointer,
-                                                          jlong termPointer,
-                                                          jboolean global)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer =
-      new Term(solver->defineFunRec(cSymbol, vars, *sort, *term, (bool)global));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    defineFunRec
- * Signature: (JJ[JJZ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_defineFunRec__JJ_3JJZ(JNIEnv* env,
-                                       jobject,
-                                       jlong pointer,
-                                       jlong funPointer,
-                                       jlongArray jVars,
-                                       jlong termPointer,
-                                       jboolean global)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* fun = reinterpret_cast<Term*>(funPointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer =
-      new Term(solver->defineFunRec(*fun, vars, *term, (bool)global));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    defineFunsRec
- * Signature: (J[J[[J[JZ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_defineFunsRec(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jlongArray jFuns,
-                                                      jobjectArray jVars,
-                                                      jlongArray jTerms,
-                                                      jboolean global)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> funs = getObjectsFromPointers<Term>(env, jFuns);
-  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
-  std::vector<std::vector<Term>> varsMatrix;
-  jsize rows = env->GetArrayLength(jVars);
-  for (jint i = 0; i < rows; i++)
-  {
-    std::vector<Term> vars;
-    jlongArray row = (jlongArray)env->GetObjectArrayElement(jVars, i);
-    jsize columns = env->GetArrayLength(row);
-    jlong* columnElements = env->GetLongArrayElements(row, nullptr);
-    for (jint j = 0; j < columns; j++)
-    {
-      Term* var = reinterpret_cast<Term*>((jlongArray)columnElements[j]);
-      vars.push_back(*var);
-    }
-    varsMatrix.push_back(vars);
-  }
-  solver->defineFunsRec(funs, varsMatrix, terms, (bool)global);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getAssertions
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_getAssertions(JNIEnv* env,
-                                                            jobject,
-                                                            jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> assertions = solver->getAssertions();
-  jlongArray ret = getPointersFromObjects<Term>(env, assertions);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getInfo
- * Signature: (JLjava/lang/String;)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Solver_getInfo(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer,
-                                                   jstring jFlag)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jFlag, nullptr);
-  std::string cFlag(s);
-  env->ReleaseStringUTFChars(jFlag, s);
-  return env->NewStringUTF(solver->getInfo(cFlag).c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getOption
- * Signature: (JLjava/lang/String;)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Solver_getOption(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jstring jOption)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jOption, nullptr);
-  std::string cOption(s);
-  env->ReleaseStringUTFChars(jOption, s);
-  return env->NewStringUTF(solver->getOption(cOption).c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getOptionNames
- * Signature: (J)[Ljava/lang/String;
- */
-JNIEXPORT jobjectArray JNICALL Java_cvc5_Solver_getOptionNames(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<std::string> options = solver->getOptionNames();
-  jobjectArray ret = getStringArrayFromStringVector(env, options);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getOptionInfo
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getOptionInfo(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jstring jOption)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::string cOption(env->GetStringUTFChars(jOption, nullptr));
-  OptionInfo* ret = new OptionInfo(solver->getOptionInfo(cOption));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getDriverOptions
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getDriverOptions(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  DriverOptions* ret = new DriverOptions(solver->getDriverOptions());
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getUnsatAssumptions
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_getUnsatAssumptions(JNIEnv* env,
-                                                                  jobject,
-                                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> core = solver->getUnsatAssumptions();
-  jlongArray ret = getPointersFromObjects<Term>(env, core);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getUnsatCore
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_getUnsatCore(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> core = solver->getUnsatCore();
-  jlongArray ret = getPointersFromObjects<Term>(env, core);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getDifficulty
- * Signature: (J)Ljava/util/Map;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_Solver_getDifficulty(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::map<Term, Term> map = solver->getDifficulty();
-  // HashMap hashMap = new HashMap();
-  jclass hashMapClass = env->FindClass("Ljava/util/HashMap;");
-  jmethodID constructor = env->GetMethodID(hashMapClass, "<init>", "()V");
-  jobject hashMap = env->NewObject(hashMapClass, constructor);
-  jmethodID putMethod = env->GetMethodID(
-      hashMapClass,
-      "put",
-      "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;");
-
-  // Long longObject = new Long(statPointer)
-  jclass longClass = env->FindClass("Ljava/lang/Long;");
-  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
-
-  for (const auto& [k, v] : map)
-  {
-    // hashmap.put(key, value);
-    Term* termKey = new Term(k);
-    Term* termValue = new Term(v);
-    jobject key = env->NewObject(
-        longClass, longConstructor, reinterpret_cast<jlong>(termKey));
-    jobject value = env->NewObject(
-        longClass, longConstructor, reinterpret_cast<jlong>(termValue));
-    env->CallObjectMethod(hashMap, putMethod, key, value);
-  }
-  return hashMap;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getProof
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Solver_getProof(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::string proof = solver->getProof();
-  return env->NewStringUTF(proof.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getValue
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getValue__JJ(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* retPointer = new Term(solver->getValue(*term));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getValue
- * Signature: (J[J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_getValue__J_3J(
-    JNIEnv* env, jobject, jlong pointer, jlongArray termPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> terms = getObjectsFromPointers<Term>(env, termPointers);
-  std::vector<Term> values = solver->getValue(terms);
-  jlongArray ret = getPointersFromObjects<Term>(env, values);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getModelDomainElements
- * Signature: (JJ)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_getModelDomainElements(
-    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  std::vector<Term> terms = solver->getModelDomainElements(*sort);
-  jlongArray ret = getPointersFromObjects<Term>(env, terms);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    isModelCoreSymbol
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Solver_isModelCoreSymbol(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer,
-                                                              jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  return static_cast<jboolean>(solver->isModelCoreSymbol(*term));
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getModel
- * Signature: (J[J[J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Solver_getModel(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jlongArray sortPointers,
-                                                    jlongArray varPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, varPointers);
-  std::string model = solver->getModel(sorts, vars);
-  return env->NewStringUTF(model.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getQuantifierElimination
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getQuantifierElimination(
-    JNIEnv* env, jobject, jlong pointer, jlong qPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* q = reinterpret_cast<Term*>(qPointer);
-  Term* retPointer = new Term(solver->getQuantifierElimination(*q));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getQuantifierEliminationDisjunct
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getQuantifierEliminationDisjunct(
-    JNIEnv* env, jobject, jlong pointer, jlong qPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* q = reinterpret_cast<Term*>(qPointer);
-  Term* retPointer = new Term(solver->getQuantifierEliminationDisjunct(*q));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    declareSeparationHeap
- * Signature: (JJJ)V
- */
-JNIEXPORT void JNICALL
-Java_cvc5_Solver_declareSeparationHeap(JNIEnv* env,
-                                       jobject,
-                                       jlong pointer,
-                                       jlong locSortPointer,
-                                       jlong dataSortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* locSort = reinterpret_cast<Sort*>(locSortPointer);
-  Sort* dataSort = reinterpret_cast<Sort*>(dataSortPointer);
-  solver->declareSeparationHeap(*locSort, *dataSort);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getSeparationHeap
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getSeparationHeap(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->getSeparationHeap());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getSeparationNilTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getSeparationNilTerm(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* retPointer = new Term(solver->getSeparationNilTerm());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    pop
- * Signature: (JI)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_pop(JNIEnv* env,
-                                            jobject,
-                                            jlong pointer,
-                                            jint nscopes)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  solver->pop((uint32_t)nscopes);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getInterpolant
- * Signature: (JJJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Solver_getInterpolant__JJJ(
-    JNIEnv* env, jobject, jlong pointer, jlong conjPointer, jlong outputPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* conj = reinterpret_cast<Term*>(conjPointer);
-  Term* output = reinterpret_cast<Term*>(outputPointer);
-  return (jboolean)solver->getInterpolant(*conj, *output);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getInterpolant
- * Signature: (JJJJ)Z
- */
-JNIEXPORT jboolean JNICALL
-Java_cvc5_Solver_getInterpolant__JJJJ(JNIEnv* env,
-                                      jobject,
-                                      jlong pointer,
-                                      jlong conjPointer,
-                                      jlong grammarPointer,
-                                      jlong outputPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* conj = reinterpret_cast<Term*>(conjPointer);
-  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
-  Term* output = reinterpret_cast<Term*>(outputPointer);
-  return (jboolean)solver->getInterpolant(*conj, *grammar, *output);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getAbduct
- * Signature: (JJJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Solver_getAbduct__JJJ(
-    JNIEnv* env, jobject, jlong pointer, jlong conjPointer, jlong outputPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* conj = reinterpret_cast<Term*>(conjPointer);
-  Term* output = reinterpret_cast<Term*>(outputPointer);
-  return (jboolean)solver->getAbduct(*conj, *output);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getAbduct
- * Signature: (JJJJ)Z
- */
-JNIEXPORT jboolean JNICALL
-Java_cvc5_Solver_getAbduct__JJJJ(JNIEnv* env,
-                                 jobject,
-                                 jlong pointer,
-                                 jlong conjPointer,
-                                 jlong grammarPointer,
-                                 jlong outputPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* conj = reinterpret_cast<Term*>(conjPointer);
-  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
-  Term* output = reinterpret_cast<Term*>(outputPointer);
-  return (jboolean)solver->getAbduct(*conj, *grammar, *output);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    blockModel
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_blockModel(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  solver->blockModel();
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    blockModelValues
- * Signature: (J[J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_blockModelValues(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer,
-                                                         jlongArray jTerms)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
-  solver->blockModelValues(terms);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    push
- * Signature: (JI)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_push(JNIEnv* env,
-                                             jobject,
-                                             jlong pointer,
-                                             jint nscopes)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  solver->push((uint32_t)nscopes);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    resetAssertions
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_resetAssertions(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  solver->resetAssertions();
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    setInfo
- * Signature: (JLjava/lang/String;Ljava/lang/String;)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_setInfo(
-    JNIEnv* env, jobject, jlong pointer, jstring jKeyword, jstring jValue)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* sKeyword = env->GetStringUTFChars(jKeyword, nullptr);
-  const char* sValue = env->GetStringUTFChars(jValue, nullptr);
-  std::string cKeyword(sKeyword);
-  std::string cValue(sValue);
-  solver->setInfo(cKeyword, cValue);
-  env->ReleaseStringUTFChars(jKeyword, sKeyword);
-  env->ReleaseStringUTFChars(jValue, sValue);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    setLogic
- * Signature: (JLjava/lang/String;)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_setLogic(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer,
-                                                 jstring jLogic)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* cLogic = env->GetStringUTFChars(jLogic, nullptr);
-  solver->setLogic(std::string(cLogic));
-
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    setOption
- * Signature: (JLjava/lang/String;Ljava/lang/String;)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_setOption(
-    JNIEnv* env, jobject, jlong pointer, jstring jOption, jstring jValue)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* sOption = env->GetStringUTFChars(jOption, nullptr);
-  const char* sValue = env->GetStringUTFChars(jValue, nullptr);
-  std::string cOption(sOption);
-  std::string cValue(sValue);
-  solver->setOption(cOption, cValue);
-  env->ReleaseStringUTFChars(jOption, sOption);
-  env->ReleaseStringUTFChars(jValue, sValue);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    ensureTermSort
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_ensureTermSort(
-    JNIEnv* env, jobject, jlong pointer, jlong termPointer, jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Term* retPointer = new Term(solver->ensureTermSort(*term, *sort));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSygusVar
- * Signature: (JJLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSygusVar(
-    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jstring jSymbol)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  Term* retPointer = new Term(solver->mkSygusVar(*sort, cSymbol));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    mkSygusGrammar
- * Signature: (J[J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_mkSygusGrammar(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jlongArray jBoundVars,
-                                                        jlongArray jNtSymbols)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> boundVars = getObjectsFromPointers<Term>(env, jBoundVars);
-  std::vector<Term> ntSymbols = getObjectsFromPointers<Term>(env, jNtSymbols);
-  Grammar* retPointer =
-      new Grammar(solver->mkSygusGrammar(boundVars, ntSymbols));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    synthFun
- * Signature: (JLjava/lang/String;[JJ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_synthFun__JLjava_lang_String_2_3JJ(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jstring jSymbol,
-                                                    jlongArray jVars,
-                                                    jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Term> boundVars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer = new Term(solver->synthFun(cSymbol, boundVars, *sort));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    synthFun
- * Signature: (JLjava/lang/String;[JJJ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_synthFun__JLjava_lang_String_2_3JJJ(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer,
-                                                     jstring jSymbol,
-                                                     jlongArray jVars,
-                                                     jlong sortPointer,
-                                                     jlong grammarPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Term> boundVars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer =
-      new Term(solver->synthFun(cSymbol, boundVars, *sort, *grammar));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    synthInv
- * Signature: (JLjava/lang/String;[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_synthInv__JLjava_lang_String_2_3J(
-    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jlongArray jVars)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer = new Term(solver->synthInv(cSymbol, vars));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    synthInv
- * Signature: (JLjava/lang/String;[JJ)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Solver_synthInv__JLjava_lang_String_2_3JJ(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer,
-                                                    jstring jSymbol,
-                                                    jlongArray jVars,
-                                                    jlong grammarPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
-  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
-  std::string cSymbol(s);
-  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
-  Term* retPointer = new Term(solver->synthInv(cSymbol, vars, *grammar));
-  env->ReleaseStringUTFChars(jSymbol, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    addSygusConstraint
- * Signature: (JJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_addSygusConstraint(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer,
-                                                           jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  solver->addSygusConstraint(*term);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    addSygusAssume
- * Signature: (JJ)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Solver_addSygusAssume(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  solver->addSygusAssume(*term);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    addSygusInvConstraint
- * Signature: (JJJJJ)V
- */
-JNIEXPORT void JNICALL
-Java_cvc5_Solver_addSygusInvConstraint(JNIEnv* env,
-                                       jobject,
-                                       jlong pointer,
-                                       jlong invPointer,
-                                       jlong prePointer,
-                                       jlong transPointer,
-                                       jlong postPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* inv = reinterpret_cast<Term*>(invPointer);
-  Term* pre = reinterpret_cast<Term*>(prePointer);
-  Term* trans = reinterpret_cast<Term*>(transPointer);
-  Term* post = reinterpret_cast<Term*>(postPointer);
-  solver->addSygusInvConstraint(*inv, *pre, *trans, *post);
-  CVC5_JAVA_API_TRY_CATCH_END(env);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    checkSynth
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_checkSynth(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Result* retPointer = new Result(solver->checkSynth());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getSynthSolution
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getSynthSolution(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer,
-                                                          jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* retPointer = new Term(solver->getSynthSolution(*term));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getSynthSolutions
- * Signature: (J[J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Solver_getSynthSolutions(
-    JNIEnv* env, jobject, jlong pointer, jlongArray jTerms)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
-  std::vector<Term> solutions = solver->getSynthSolutions(terms);
-  jlongArray ret = getPointersFromObjects<Term>(env, solutions);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getStatistics
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getStatistics(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Solver* solver = reinterpret_cast<Solver*>(pointer);
-  Statistics* retPointer = new Statistics(solver->getStatistics());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getNullTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getNullTerm(JNIEnv* env,
-                                                     jobject,
-                                                     jlong)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* ret = new Term();
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getNullResult
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getNullResult(JNIEnv* env,
-                                                       jobject,
-                                                       jlong)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Result* ret = new Result();
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getNullOp
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getNullOp(JNIEnv* env, jobject, jlong)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Op* ret = new Op();
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Solver
- * Method:    getNullDatatypeDecl
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Solver_getNullDatatypeDecl(JNIEnv* env,
-                                                             jobject,
-                                                             jlong)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  DatatypeDecl* ret = new DatatypeDecl();
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
diff --git a/src/api/java/jni/cvc5_Sort.cpp b/src/api/java/jni/cvc5_Sort.cpp
deleted file mode 100644 (file)
index 36ba812..0000000
+++ /dev/null
@@ -1,1096 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Sort.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Sort
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Sort_deletePointer(JNIEnv*,
-                                                    jclass,
-                                                    jlong pointer)
-{
-  delete reinterpret_cast<Sort*>(pointer);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    equals
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_equals(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer1,
-                                                 jlong pointer2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort sort1 = *(reinterpret_cast<Sort*>(pointer1));
-  Sort sort2 = *(reinterpret_cast<Sort*>(pointer2));
-  return static_cast<jboolean>((sort1 == sort2));
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    compareTo
- * Signature: (JJ)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_compareTo(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer1,
-                                                jlong pointer2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* sort1 = reinterpret_cast<Sort*>(pointer1);
-  Sort* sort2 = reinterpret_cast<Sort*>(pointer2);
-  if (*sort1 < *sort2)
-  {
-    return static_cast<jint>(-1);
-  }
-  if (*sort1 == *sort2)
-  {
-    return 0;
-  }
-  return static_cast<jint>(1);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isNull(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isNull());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isBoolean
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isBoolean(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isBoolean());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isInteger
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isInteger(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isInteger());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isReal
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isReal(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isReal());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isString
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isString(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isString());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isRegExp
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isRegExp(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isRegExp());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isRoundingMode
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isRoundingMode(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isRoundingMode());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isBitVector
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isBitVector(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isBitVector());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isFloatingPoint
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isFloatingPoint(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPoint());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isDatatype
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isDatatype(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isDatatype());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isParametricDatatype
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isParametricDatatype(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isParametricDatatype());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isConstructor
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isConstructor(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isConstructor());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isSelector
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isSelector(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isSelector());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isTester
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isTester(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isTester());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isUpdater
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isUpdater(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isUpdater());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isFunction
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isFunction(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isFunction());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isPredicate
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isPredicate(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isPredicate());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isTuple
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isTuple(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isTuple());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isRecord
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isRecord(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isRecord());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isArray
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isArray(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isArray());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isSet
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isSet(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isSet());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isBag
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isBag(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isBag());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isSequence
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isSequence(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isSequence());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isUninterpretedSort
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isUninterpretedSort(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isUninterpretedSort());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isSortConstructor
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isSortConstructor(JNIEnv* env,
-                                                            jobject,
-                                                            jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isSortConstructor());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isFirstClass
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isFirstClass(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isFirstClass());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isFunctionLike
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isFunctionLike(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isFunctionLike());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isSubsortOf
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isSubsortOf(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer,
-                                                      jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  return static_cast<jboolean>(current->isSubsortOf(*sort));
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isComparableTo
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isComparableTo(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer,
-                                                         jlong sortPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  return static_cast<jboolean>(current->isComparableTo(*sort));
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getDatatype
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getDatatype(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Datatype* retPointer = new Datatype(current->getDatatype());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    instantiate
- * Signature: (J[J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_instantiate(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer,
-                                                   jlongArray paramsPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  // get the size of params pointers
-  jsize size = env->GetArrayLength(paramsPointers);
-  // allocate buffer for the long array
-  jlong* buffer = new jlong[size];
-  // copy java array to the buffer
-  env->GetLongArrayRegion(paramsPointers, 0, size, buffer);
-  // copy the terms into a vector
-  std::vector<Sort> params;
-  for (jsize i = 0; i < size; i++)
-  {
-    Sort* sort = reinterpret_cast<Sort*>(buffer[i]);
-    params.push_back(*sort);
-  }
-  // free the buffer memory
-  delete[] buffer;
-
-  Sort* retPointer = new Sort(current->instantiate(params));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    substitute
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_substitute__JJJ(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong sortPointer,
-                                                       jlong replacementPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
-  Sort* replacement = reinterpret_cast<Sort*>(replacementPointer);
-  Sort* retPointer = new Sort(current->substitute(*sort, *replacement));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    substitute
- * Signature: (J[J[J)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Sort_substitute__J_3J_3J(JNIEnv* env,
-                                   jobject,
-                                   jlong pointer,
-                                   jlongArray sortPointers,
-                                   jlongArray replacementPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  // get the size of pointers
-  jsize sortsSize = env->GetArrayLength(sortPointers);
-  jsize replacementsSize = env->GetArrayLength(replacementPointers);
-  // allocate buffer for the long array
-  jlong* sortsBuffer = new jlong[sortsSize];
-  jlong* replacementsBuffer = new jlong[replacementsSize];
-  // copy java array to the buffer
-  env->GetLongArrayRegion(sortPointers, 0, sortsSize, sortsBuffer);
-  env->GetLongArrayRegion(
-      replacementPointers, 0, replacementsSize, replacementsBuffer);
-  // copy the terms into a vector
-  std::vector<Sort> sorts;
-  for (jsize i = 0; i < sortsSize; i++)
-  {
-    Sort* sort = reinterpret_cast<Sort*>(sortsBuffer[i]);
-    sorts.push_back(*sort);
-  }
-
-  std::vector<Sort> replacements;
-  for (jsize i = 0; i < replacementsSize; i++)
-  {
-    Sort* sort = reinterpret_cast<Sort*>(replacementsBuffer[i]);
-    replacements.push_back(*sort);
-  }
-
-  // free the buffer memory
-  delete[] sortsBuffer;
-  delete[] replacementsBuffer;
-
-  Sort* retPointer = new Sort(current->substitute(sorts, replacements));
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Sort_toString(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getConstructorArity
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getConstructorArity(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getConstructorArity());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getConstructorDomainSorts
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL
-Java_cvc5_Sort_getConstructorDomainSorts(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  std::vector<Sort> sorts = current->getConstructorDomainSorts();
-  std::vector<long> sortPointers(sorts.size());
-  for (size_t i = 0; i < sorts.size(); i++)
-  {
-    sortPointers[i] = (long)new Sort(sorts[i]);
-  }
-  jlongArray ret = env->NewLongArray(sorts.size());
-  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getConstructorCodomainSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getConstructorCodomainSort(JNIEnv* env,
-                                                                  jobject,
-                                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getConstructorCodomainSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getSelectorDomainSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getSelectorDomainSort(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getSelectorDomainSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getSelectorCodomainSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getSelectorCodomainSort(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getSelectorCodomainSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getTesterDomainSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getTesterDomainSort(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getTesterDomainSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getTesterCodomainSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getTesterCodomainSort(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getTesterCodomainSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getFunctionArity
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getFunctionArity(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getFunctionArity());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getFunctionDomainSorts
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL
-Java_cvc5_Sort_getFunctionDomainSorts(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  std::vector<Sort> sorts = current->getFunctionDomainSorts();
-  std::vector<long> sortPointers(sorts.size());
-  for (size_t i = 0; i < sorts.size(); i++)
-  {
-    sortPointers[i] = (long)new Sort(sorts[i]);
-  }
-  jlongArray ret = env->NewLongArray(sorts.size());
-  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getFunctionCodomainSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getFunctionCodomainSort(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getFunctionCodomainSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getArrayIndexSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getArrayIndexSort(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getArrayIndexSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getArrayElementSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getArrayElementSort(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getArrayElementSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getSetElementSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getSetElementSort(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getSetElementSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getBagElementSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getBagElementSort(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getBagElementSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getSequenceElementSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Sort_getSequenceElementSort(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  Sort* retPointer = new Sort(current->getSequenceElementSort());
-  return (jlong)retPointer;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getUninterpretedSortName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Sort_getUninterpretedSortName(JNIEnv* env,
-                                                                  jobject,
-                                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return env->NewStringUTF(current->getUninterpretedSortName().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    isUninterpretedSortParameterized
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Sort_isUninterpretedSortParameterized(
-    JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jboolean>(current->isUninterpretedSortParameterized());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getUninterpretedSortParamSorts
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Sort_getUninterpretedSortParamSorts(
-    JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  std::vector<Sort> sorts = current->getUninterpretedSortParamSorts();
-  std::vector<long> sortPointers(sorts.size());
-  for (size_t i = 0; i < sorts.size(); i++)
-  {
-    sortPointers[i] = (long)new Sort(sorts[i]);
-  }
-  jlongArray ret = env->NewLongArray(sorts.size());
-  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getSortConstructorName
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Sort_getSortConstructorName(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return env->NewStringUTF(current->getSortConstructorName().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getSortConstructorArity
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getSortConstructorArity(JNIEnv* env,
-                                                              jobject,
-                                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getSortConstructorArity());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getBitVectorSize
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getBitVectorSize(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getBitVectorSize());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getFloatingPointExponentSize
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL
-Java_cvc5_Sort_getFloatingPointExponentSize(JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getFloatingPointExponentSize());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getFloatingPointSignificandSize
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getFloatingPointSignificandSize(
-    JNIEnv* env, jobject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getFloatingPointSignificandSize());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getDatatypeParamSorts
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Sort_getDatatypeParamSorts(JNIEnv* env,
-                                                                  jobject,
-                                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  std::vector<Sort> sorts = current->getDatatypeParamSorts();
-  std::vector<long> sortPointers(sorts.size());
-  for (size_t i = 0; i < sorts.size(); i++)
-  {
-    sortPointers[i] = (long)new Sort(sorts[i]);
-  }
-  jlongArray ret = env->NewLongArray(sorts.size());
-  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getDatatypeArity
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getDatatypeArity(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getDatatypeArity());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getTupleLength
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Sort_getTupleLength(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  return static_cast<jint>(current->getTupleLength());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Sort
- * Method:    getTupleSorts
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Sort_getTupleSorts(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Sort* current = reinterpret_cast<Sort*>(pointer);
-  std::vector<Sort> sorts = current->getTupleSorts();
-  std::vector<long> sortPointers(sorts.size());
-  for (size_t i = 0; i < sorts.size(); i++)
-  {
-    sortPointers[i] = (long)new Sort(sorts[i]);
-  }
-  jlongArray ret = env->NewLongArray(sorts.size());
-  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_Stat.cpp b/src/api/java/jni/cvc5_Stat.cpp
deleted file mode 100644 (file)
index 9345729..0000000
+++ /dev/null
@@ -1,223 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Stat.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Stat
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Stat_deletePointer(JNIEnv*,
-                                                    jclass,
-                                                    jlong pointer)
-{
-  delete reinterpret_cast<Stat*>(pointer);
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Stat_toString(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  std::stringstream ss;
-  ss << *current;
-  return env->NewStringUTF(ss.str().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    isExpert
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Stat_isExpert(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jboolean>(current->isExpert());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    isDefault
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Stat_isDefault(JNIEnv* env,
-                                                    jobject,
-                                                    jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jboolean>(current->isDefault());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    isInt
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Stat_isInt(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jboolean>(current->isInt());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    getInt
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Stat_getInt(JNIEnv* env,
-                                              jobject,
-                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jlong>(current->getInt());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jlong>(0));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    isDouble
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Stat_isDouble(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jboolean>(current->isDouble());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    getDouble
- * Signature: (J)D
- */
-JNIEXPORT jdouble JNICALL Java_cvc5_Stat_getDouble(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jdouble>(current->getDouble());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jdouble>(0));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    isString
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Stat_isString(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jboolean>(current->isString());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    getString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Stat_getString(JNIEnv* env,
-                                                   jobject,
-                                                   jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return env->NewStringUTF(current->getString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    isHistogram
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Stat_isHistogram(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  return static_cast<jboolean>(current->isHistogram());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Stat
- * Method:    getHistogram
- * Signature: (J)Ljava/util/Map;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_Stat_getHistogram(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Stat* current = reinterpret_cast<Stat*>(pointer);
-  std::map<std::string, uint64_t> histogram = current->getHistogram();
-  // HashMap hashMap = new HashMap();
-  jclass hashMapClass = env->FindClass("Ljava/util/HashMap;");
-  jmethodID constructor = env->GetMethodID(hashMapClass, "<init>", "()V");
-  jobject hashMap = env->NewObject(hashMapClass, constructor);
-  jmethodID putMethod = env->GetMethodID(
-      hashMapClass,
-      "put",
-      "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;");
-
-  // Long longObject = new Long(statPointer)
-  jclass longClass = env->FindClass("Ljava/lang/Long;");
-  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
-
-  for (const std::pair<const std::basic_string<char>, uint64_t>& it : histogram)
-  {
-    // hashmap.put(key, value);
-    jstring key = env->NewStringUTF(it.first.c_str());
-    jobject value = env->NewObject(
-        longClass, longConstructor, static_cast<jlong>(it.second));
-    env->CallObjectMethod(hashMap, putMethod, key, value);
-  }
-  return hashMap;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
diff --git a/src/api/java/jni/cvc5_Statistics.cpp b/src/api/java/jni/cvc5_Statistics.cpp
deleted file mode 100644 (file)
index 8db2e15..0000000
+++ /dev/null
@@ -1,180 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Statistics.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-#include <sstream>
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Statistics
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Statistics_deletePointer(JNIEnv*,
-                                                          jclass,
-                                                          jlong pointer)
-{
-  delete reinterpret_cast<Statistics*>(pointer);
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Statistics_toString(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-
-  Statistics* current = reinterpret_cast<Statistics*>(pointer);
-  std::stringstream ss;
-  ss << *current;
-  return env->NewStringUTF(ss.str().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    get
- * Signature: (JLjava/lang/String;)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Statistics_get(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer,
-                                                 jstring jName)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Statistics* current = reinterpret_cast<Statistics*>(pointer);
-  const char* s = env->GetStringUTFChars(jName, nullptr);
-  std::string cName(s);
-  Stat* retPointer = new Stat(current->get(cName));
-  env->ReleaseStringUTFChars(jName, s);
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    getIterator
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Statistics_getIterator(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Statistics* current = reinterpret_cast<Statistics*>(pointer);
-  Statistics::iterator* it =
-      new Statistics::iterator(current->begin(true, true));
-  return reinterpret_cast<jlong>(it);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    hasNext
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Statistics_hasNext(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer,
-                                                        jlong iteratorPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Statistics* current = reinterpret_cast<Statistics*>(pointer);
-  Statistics::iterator it =
-      *reinterpret_cast<Statistics::iterator*>(iteratorPointer);
-  return static_cast<jboolean>(it != current->end());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    getNext
- * Signature: (JJ)Lcvc5/Pair;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_Statistics_getNext(JNIEnv* env,
-                                                       jobject,
-                                                       jlong,
-                                                       jlong iteratorPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Statistics::iterator it =
-      *reinterpret_cast<Statistics::iterator*>(iteratorPointer);
-  std::string cName = it->first;
-  jstring jName = env->NewStringUTF(cName.c_str());
-  Stat* stat = new Stat(it->second);
-  jlong statPointer = reinterpret_cast<jlong>(stat);
-
-  // Long longObject = new Long(statPointer)
-  jclass longClass = env->FindClass("Ljava/lang/Long;");
-  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
-  jobject longObject = env->NewObject(longClass, longConstructor, statPointer);
-
-  // Pair<String, Long> pair = new Pair<String, Long>(jName, longObject)
-  jclass pairClass = env->FindClass("Lcvc5/Pair;");
-  jmethodID pairConstructor = env->GetMethodID(
-      pairClass, "<init>", "(Ljava/lang/Object;Ljava/lang/Object;)V");
-  jobject pair = env->NewObject(pairClass, pairConstructor, jName, longObject);
-
-  it++;
-  return pair;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    increment
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Statistics_increment(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong iteratorPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Statistics* current = reinterpret_cast<Statistics*>(pointer);
-  Statistics::iterator* itPointer =
-      reinterpret_cast<Statistics::iterator*>(iteratorPointer);
-  Statistics::iterator it = *itPointer;
-  if (it == current->end())
-  {
-    delete itPointer;
-    std::string message = "Reached the end of Statistics::iterator";
-    throw CVC5ApiException(message);
-  }
-
-  Statistics::iterator* nextIt = new Statistics::iterator(it.operator++());
-  delete itPointer;
-  return reinterpret_cast<jlong>(nextIt);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Statistics
- * Method:    deleteIteratorPointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Statistics_deleteIteratorPointer(
-    JNIEnv*, jobject, jlong iteratorPointer)
-{
-  delete reinterpret_cast<Statistics::iterator*>(iteratorPointer);
-}
diff --git a/src/api/java/jni/cvc5_Term.cpp b/src/api/java/jni/cvc5_Term.cpp
deleted file mode 100644 (file)
index 325a9c7..0000000
+++ /dev/null
@@ -1,925 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * The cvc5 Java API.
- */
-
-#include "cvc5_Term.h"
-
-#include "api/cpp/cvc5.h"
-#include "cvc5JavaApi.h"
-
-using namespace cvc5::api;
-
-/*
- * Class:     cvc5_Term
- * Method:    deletePointer
- * Signature: (J)V
- */
-JNIEXPORT void JNICALL Java_cvc5_Term_deletePointer(JNIEnv* env,
-                                                    jclass,
-                                                    jlong pointer)
-{
-  delete reinterpret_cast<Term*>(pointer);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    equals
- * Signature: (JJ)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_equals(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer1,
-                                                 jlong pointer2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* term1 = reinterpret_cast<Term*>(pointer1);
-  Term* term2 = reinterpret_cast<Term*>(pointer2);
-  // We compare the actual terms, not their pointers.
-  return static_cast<jboolean>(*term1 == *term2);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    compareTo
- * Signature: (JJ)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Term_compareTo(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer1,
-                                                jlong pointer2)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* term1 = reinterpret_cast<Term*>(pointer1);
-  Term* term2 = reinterpret_cast<Term*>(pointer2);
-  if (*term1 < *term2)
-  {
-    return static_cast<jint>(-1);
-  }
-  if (*term1 == *term2)
-  {
-    return 0;
-  }
-  return static_cast<jint>(1);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getNumChildren
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Term_getNumChildren(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jint>(current->getNumChildren());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getChild
- * Signature: (JI)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_getChild(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer,
-                                                jint index)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* ret = new Term((*current)[static_cast<size_t>(index)]);
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getId
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_getId(JNIEnv* env,
-                                             jobject,
-                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jlong>(current->getId());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getKind
- * Signature: (J)I
- */
-JNIEXPORT jint JNICALL Java_cvc5_Term_getKind(JNIEnv* env,
-                                              jobject,
-                                              jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jint>(current->getKind());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getSort
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_getSort(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Sort* ret = new Sort(current->getSort());
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    substitute
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_substitute__JJJ(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer,
-                                                       jlong termPointer,
-                                                       jlong replacementPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* replacement = reinterpret_cast<Term*>(replacementPointer);
-  Term* ret = new Term(current->substitute(*term, *replacement));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    substitute
- * Signature: (J[J[J)J
- */
-JNIEXPORT jlong JNICALL
-Java_cvc5_Term_substitute__J_3J_3J(JNIEnv* env,
-                                   jobject,
-                                   jlong pointer,
-                                   jlongArray termPointers,
-                                   jlongArray replacementPointers)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  jsize termsSize = env->GetArrayLength(termPointers);
-  jsize replacementsSize = env->GetArrayLength(replacementPointers);
-  jlong* termElements = env->GetLongArrayElements(termPointers, nullptr);
-  jlong* replacementElements =
-      env->GetLongArrayElements(replacementPointers, nullptr);
-
-  std::vector<Term> terms(termsSize);
-  std::vector<Term> replacements(replacementsSize);
-
-  for (jsize i = 0; i < termsSize; i++)
-  {
-    Term* term = (Term*)termElements[i];
-    terms[i] = *term;
-  }
-  env->ReleaseLongArrayElements(termPointers, termElements, 0);
-
-  for (jsize i = 0; i < replacementsSize; i++)
-  {
-    Term* term = (Term*)replacementElements[i];
-    replacements[i] = *term;
-  }
-  env->ReleaseLongArrayElements(replacementPointers, replacementElements, 0);
-
-  Term* ret = new Term(current->substitute(terms, replacements));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    hasOp
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_hasOp(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->hasOp());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getOp
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_getOp(JNIEnv* env,
-                                             jobject,
-                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Op* ret = new Op(current->getOp());
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isNull
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isNull(JNIEnv* env,
-                                                 jobject,
-                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isNull());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isConstArray
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isConstArray(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isConstArray());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getConstArrayBase
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_getConstArrayBase(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* ret = new Term(current->getConstArrayBase());
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    notTerm
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_notTerm(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* ret = new Term(current->notTerm());
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    andTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_andTerm(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer,
-                                               jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* ret = new Term(current->andTerm(*term));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    orTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_orTerm(JNIEnv* env,
-                                              jobject,
-                                              jlong pointer,
-                                              jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* ret = new Term(current->orTerm(*term));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    xorTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_xorTerm(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer,
-                                               jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* ret = new Term(current->xorTerm(*term));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    eqTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_eqTerm(JNIEnv* env,
-                                              jobject,
-                                              jlong pointer,
-                                              jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* ret = new Term(current->eqTerm(*term));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    impTerm
- * Signature: (JJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_impTerm(JNIEnv* env,
-                                               jobject,
-                                               jlong pointer,
-                                               jlong termPointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* term = reinterpret_cast<Term*>(termPointer);
-  Term* ret = new Term(current->impTerm(*term));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    iteTerm
- * Signature: (JJJ)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_iteTerm(
-    JNIEnv* env, jobject, jlong pointer, jlong thenPointer, jlong elsePointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term* thenTerm = reinterpret_cast<Term*>(thenPointer);
-  Term* elseTerm = reinterpret_cast<Term*>(elsePointer);
-  Term* ret = new Term(current->iteTerm(*thenTerm, *elseTerm));
-  return reinterpret_cast<jlong>(ret);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    toString
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Term_toString(JNIEnv* env,
-                                                  jobject,
-                                                  jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return env->NewStringUTF(current->toString().c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isIntegerValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isIntegerValue(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isIntegerValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getIntegerValue
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Term_getIntegerValue(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::string value = current->getIntegerValue();
-  jstring ret = env->NewStringUTF(value.c_str());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isStringValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isStringValue(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isStringValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getStringValue
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Term_getStringValue(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::wstring termString = current->getStringValue();
-
-  size_t length = termString.length();
-  jchar* unicode = new jchar[length];
-  const wchar_t* s = termString.c_str();
-  for (size_t i = 0; i < length; i++)
-  {
-    unicode[i] = s[i];
-  }
-  jstring ret = env->NewString(unicode, length);
-  delete[] unicode;
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isRealValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isRealValue(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isRealValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getRealValue
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Term_getRealValue(JNIEnv* env,
-                                                      jobject,
-                                                      jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::string realValue = current->getRealValue();
-  return env->NewStringUTF(realValue.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isBooleanValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isBooleanValue(JNIEnv* env,
-                                                         jobject,
-                                                         jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isBooleanValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getBooleanValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_getBooleanValue(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->getBooleanValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isBitVectorValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isBitVectorValue(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isBitVectorValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getBitVectorValue
- * Signature: (JI)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Term_getBitVectorValue(JNIEnv* env,
-                                                           jobject,
-                                                           jlong pointer,
-                                                           jint base)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::string ret =
-      current->getBitVectorValue(static_cast<std::uint32_t>(base));
-  return env->NewStringUTF(ret.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isAbstractValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isAbstractValue(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isAbstractValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getAbstractValue
- * Signature: (J)Ljava/lang/String;
- */
-JNIEXPORT jstring JNICALL Java_cvc5_Term_getAbstractValue(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::string ret = current->getAbstractValue();
-  return env->NewStringUTF(ret.c_str());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isTupleValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isTupleValue(JNIEnv* env,
-                                                       jobject,
-                                                       jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isTupleValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getTupleValue
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Term_getTupleValue(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::vector<Term> terms = current->getTupleValue();
-  jlongArray ret = getPointersFromObjects<Term>(env, terms);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isFloatingPointPosZero
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isFloatingPointPosZero(JNIEnv* env,
-                                                                 jobject,
-                                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPointPosZero());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isFloatingPointNegZero
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isFloatingPointNegZero(JNIEnv* env,
-                                                                 jobject,
-                                                                 jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPointNegZero());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isFloatingPointPosInf
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isFloatingPointPosInf(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPointPosInf());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isFloatingPointNegInf
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isFloatingPointNegInf(JNIEnv* env,
-                                                                jobject,
-                                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPointNegInf());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isFloatingPointNaN
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isFloatingPointNaN(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPointNaN());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isFloatingPointValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isFloatingPointValue(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isFloatingPointValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getFloatingPointValue
- * Signature: (J)Lcvc5/Triplet;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_Term_getFloatingPointValue(
-    JNIEnv* env, jobject thisObject, jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  auto [exponent, significand, term] = current->getFloatingPointValue();
-  Term* termPointer = new Term(term);
-
-  // Long longObject = new Long(pointer)
-  jclass longClass = env->FindClass("Ljava/lang/Long;");
-  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
-  jobject e = env->NewObject(longClass, longConstructor, exponent);
-  jobject s = env->NewObject(longClass, longConstructor, significand);
-  jobject t = env->NewObject(longClass, longConstructor, termPointer);
-
-  // Triplet triplet = new Triplet<Long, Long, Long>(e, s, t);
-  jclass tripletClass = env->FindClass("Lcvc5/Triplet;");
-  jmethodID tripletConstructor = env->GetMethodID(
-      tripletClass,
-      "<init>",
-      "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V");
-  jobject triplet = env->NewObject(tripletClass, tripletConstructor, e, s, t);
-
-  return triplet;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isSetValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isSetValue(JNIEnv* env,
-                                                     jobject,
-                                                     jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isSetValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getSetValue
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Term_getSetValue(JNIEnv* env,
-                                                        jobject,
-                                                        jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::set<Term> terms = current->getSetValue();
-  std::vector<jlong> pointers(terms.size());
-  int i = 0;
-  for (const Term& t : terms)
-  {
-    pointers[i] = reinterpret_cast<jlong>(new Term(t));
-    i++;
-  }
-  jlongArray ret = env->NewLongArray(pointers.size());
-  env->SetLongArrayRegion(ret, 0, pointers.size(), pointers.data());
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isSequenceValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isSequenceValue(JNIEnv* env,
-                                                          jobject,
-                                                          jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isSequenceValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getSequenceValue
- * Signature: (J)[J
- */
-JNIEXPORT jlongArray JNICALL Java_cvc5_Term_getSequenceValue(JNIEnv* env,
-                                                             jobject,
-                                                             jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::vector<Term> terms = current->getSequenceValue();
-  jlongArray ret = getPointersFromObjects<Term>(env, terms);
-  return ret;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    isUninterpretedValue
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_cvc5_Term_isUninterpretedValue(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  return static_cast<jboolean>(current->isUninterpretedValue());
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    getUninterpretedValue
- * Signature: (J)Lcvc5/Pair;
- */
-JNIEXPORT jobject JNICALL Java_cvc5_Term_getUninterpretedValue(JNIEnv* env,
-                                                               jobject,
-                                                               jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  std::pair<Sort, std::int32_t> value = current->getUninterpretedValue();
-
-  Sort* sort = new Sort(value.first);
-  jlong sortPointer = reinterpret_cast<jlong>(sort);
-
-  // Long longObject = new Long(pointer)
-  jclass longClass = env->FindClass("Ljava/lang/Long;");
-  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
-  jobject longObject = env->NewObject(longClass, longConstructor, sortPointer);
-
-  // Integer integerObject = new Integer(pair.second)
-  jclass integerClass = env->FindClass("Ljava/lang/Integer;");
-  jmethodID integerConstructor =
-      env->GetMethodID(integerClass, "<init>", "(I)V");
-  jobject integerObject = env->NewObject(
-      integerClass, integerConstructor, static_cast<jint>(value.second));
-
-  // Pair<String, Long> pair = new Pair<String, Long>(jName, longObject)
-  jclass pairClass = env->FindClass("Lcvc5/Pair;");
-  jmethodID pairConstructor = env->GetMethodID(
-      pairClass, "<init>", "(Ljava/lang/Object;Ljava/lang/Object;)V");
-  jobject pair =
-      env->NewObject(pairClass, pairConstructor, longObject, integerObject);
-
-  return pair;
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
-}
-
-/*
- * Class:     cvc5_Term
- * Method:    iterator
- * Signature: (J)J
- */
-JNIEXPORT jlong JNICALL Java_cvc5_Term_iterator(JNIEnv* env,
-                                                jobject,
-                                                jlong pointer)
-{
-  CVC5_JAVA_API_TRY_CATCH_BEGIN;
-  Term* current = reinterpret_cast<Term*>(pointer);
-  Term::const_iterator* retPointer = new Term::const_iterator(current->begin());
-  return reinterpret_cast<jlong>(retPointer);
-  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
-}
diff --git a/src/api/java/jni/datatype.cpp b/src/api/java/jni/datatype.cpp
new file mode 100644 (file)
index 0000000..5efff9f
--- /dev/null
@@ -0,0 +1,239 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Datatype.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Datatype_deletePointer(
+    JNIEnv* env, jclass, jlong pointer)
+{
+  delete ((Datatype*)pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    getConstructor
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Datatype_getConstructor__JI(
+    JNIEnv* env, jobject, jlong pointer, jint idx)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  DatatypeConstructor* retPointer =
+      new DatatypeConstructor(current->operator[](idx));
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    getConstructor
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Datatype_getConstructor__JLjava_lang_String_2(
+    JNIEnv* env, jobject, jlong pointer, jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  DatatypeConstructor* retPointer =
+      new DatatypeConstructor(current->operator[](cName));
+  env->ReleaseStringUTFChars(jName, s);
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    getConstructorTerm
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Datatype_getConstructorTerm(
+    JNIEnv* env, jobject, jlong pointer, jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  Term* retPointer = new Term(current->getConstructorTerm(cName));
+  env->ReleaseStringUTFChars(jName, s);
+  return ((jlong)retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    getName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Datatype_getName(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return env->NewStringUTF(current->getName().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    getNumConstructors
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Datatype_getNumConstructors(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jint)current->getNumConstructors();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isParametric
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Datatype_isParametric(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isParametric();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isCodatatype
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Datatype_isCodatatype(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isCodatatype();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isTuple
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Datatype_isTuple(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isTuple();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isRecord
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Datatype_isRecord(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isRecord();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isFinite
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Datatype_isFinite(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isFinite();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isWellFounded
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Datatype_isWellFounded(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isWellFounded();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    hasNestedRecursion
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Datatype_hasNestedRecursion(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->hasNestedRecursion();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Datatype_isNull(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return (jboolean)current->isNull();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Datatype
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Datatype_toString(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Datatype* current = (Datatype*)pointer;
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/datatype_constructor.cpp b/src/api/java/jni/datatype_constructor.cpp
new file mode 100644 (file)
index 0000000..853766c
--- /dev/null
@@ -0,0 +1,202 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_DatatypeConstructor.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_deletePointer(JNIEnv*,
+                                                          jclass,
+                                                          jlong pointer)
+{
+  delete ((DatatypeConstructor*)pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_DatatypeConstructor_getName(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  return env->NewStringUTF(current->getName().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getConstructorTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getConstructorTerm(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  Term* retPointer = new Term(current->getConstructorTerm());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getSpecializedConstructorTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getSpecializedConstructorTerm(
+    JNIEnv* env, jobject, jlong pointer, jlong retSortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  Sort* sort = (Sort*)retSortPointer;
+  Term* retPointer = new Term(current->getSpecializedConstructorTerm(*sort));
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getTesterTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getTesterTerm(JNIEnv* env,
+                                                          jobject,
+                                                          jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  Term* retPointer = new Term(current->getTesterTerm());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getNumSelectors
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getNumSelectors(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  return (jint)current->getNumSelectors();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getSelector
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getSelector__JI(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer,
+                                                            jint index)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  DatatypeSelector* retPointer =
+      new DatatypeSelector(current->operator[]((size_t)index));
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getSelector
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getSelector__JLjava_lang_String_2(
+    JNIEnv* env, jobject, jlong pointer, jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  DatatypeSelector* retPointer =
+      new DatatypeSelector(current->operator[](cName));
+  env->ReleaseStringUTFChars(jName, s);
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    getSelectorTerm
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeConstructor_getSelectorTerm(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer,
+                                                            jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  Term* retPointer = new Term(current->getSelectorTerm(cName));
+  env->ReleaseStringUTFChars(jName, s);
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_DatatypeConstructor_isNull(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  return (jboolean)current->isNull();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructor
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_DatatypeConstructor_toString(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructor* current = (DatatypeConstructor*)pointer;
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/datatype_constructor_decl.cpp b/src/api/java/jni/datatype_constructor_decl.cpp
new file mode 100644 (file)
index 0000000..b13b75e
--- /dev/null
@@ -0,0 +1,104 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_DatatypeConstructorDecl.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructorDecl
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_DatatypeConstructorDecl_deletePointer(JNIEnv*,
+                                                              jclass,
+                                                              jlong pointer)
+{
+  delete ((DatatypeConstructorDecl*)pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructorDecl
+ * Method:    addSelector
+ * Signature: (JLjava/lang/String;J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_DatatypeConstructorDecl_addSelector(
+    JNIEnv* env, jobject, jlong pointer, jstring jName, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  Sort* sort = (Sort*)sortPointer;
+  current->addSelector(cName, *sort);
+  env->ReleaseStringUTFChars(jName, s);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructorDecl
+ * Method:    addSelectorSelf
+ * Signature: (JLjava/lang/String;)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_DatatypeConstructorDecl_addSelectorSelf(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer,
+                                                                jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  current->addSelectorSelf(cName);
+  env->ReleaseStringUTFChars(jName, s);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructorDecl
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_DatatypeConstructorDecl_isNull(JNIEnv* env,
+                                                       jobject,
+                                                       jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
+  return (jboolean)current->isNull();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeConstructorDecl
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_DatatypeConstructorDecl_toString(JNIEnv* env,
+                                                         jobject,
+                                                         jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeConstructorDecl* current = (DatatypeConstructorDecl*)pointer;
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/datatype_decl.cpp b/src/api/java/jni/datatype_decl.cpp
new file mode 100644 (file)
index 0000000..845afac
--- /dev/null
@@ -0,0 +1,116 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_DatatypeDecl.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_DatatypeDecl_deletePointer(
+    JNIEnv*, jclass, jlong pointer)
+{
+  delete ((DatatypeDecl*)pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    addConstructor
+ * Signature: (JJ)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_DatatypeDecl_addConstructor(
+    JNIEnv* env, jobject, jlong pointer, jlong declPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* current = (DatatypeDecl*)pointer;
+  DatatypeConstructorDecl* decl = (DatatypeConstructorDecl*)declPointer;
+  current->addConstructor(*decl);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    getNumConstructors
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_DatatypeDecl_getNumConstructors(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* current = (DatatypeDecl*)pointer;
+  return (jint)current->getNumConstructors();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    isParametric
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_DatatypeDecl_isParametric(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* current = (DatatypeDecl*)pointer;
+  return (jboolean)current->isParametric();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_DatatypeDecl_isNull(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* current = (DatatypeDecl*)pointer;
+  return (jboolean)current->isNull();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_DatatypeDecl_toString(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* current = (DatatypeDecl*)pointer;
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeDecl
+ * Method:    getName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_DatatypeDecl_getName(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* current = (DatatypeDecl*)pointer;
+  return env->NewStringUTF(current->getName().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/datatype_selector.cpp b/src/api/java/jni/datatype_selector.cpp
new file mode 100644 (file)
index 0000000..964eb24
--- /dev/null
@@ -0,0 +1,120 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_DatatypeSelector.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_DatatypeSelector_deletePointer(
+    JNIEnv*, jclass, jlong pointer)
+{
+  delete ((DatatypeSelector*)pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    getName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_DatatypeSelector_getName(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeSelector* current = (DatatypeSelector*)pointer;
+  return env->NewStringUTF(current->getName().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    getSelectorTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_DatatypeSelector_getSelectorTerm(JNIEnv* env,
+                                                         jobject,
+                                                         jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeSelector* current = (DatatypeSelector*)pointer;
+  Term* retPointer = new Term(current->getSelectorTerm());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    getUpdaterTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_DatatypeSelector_getUpdaterTerm(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeSelector* current = (DatatypeSelector*)pointer;
+  Term* retPointer = new Term(current->getUpdaterTerm());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    getRangeSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_DatatypeSelector_getRangeSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeSelector* current = (DatatypeSelector*)pointer;
+  Sort* retPointer = new Sort(current->getRangeSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_DatatypeSelector_isNull(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeSelector* current = (DatatypeSelector*)pointer;
+  return (jboolean)current->isNull();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_DatatypeSelector
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_DatatypeSelector_toString(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeSelector* current = (DatatypeSelector*)pointer;
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/grammar.cpp b/src/api/java/jni/grammar.cpp
new file mode 100644 (file)
index 0000000..4bafd54
--- /dev/null
@@ -0,0 +1,130 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Grammar.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    copyGrammar
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Grammar_copyGrammar(JNIEnv* env, jclass, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Grammar* current = reinterpret_cast<Grammar*>(pointer);
+  Grammar* retPointer = new Grammar(*current);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Grammar_deletePointer(JNIEnv*, jclass, jlong pointer)
+{
+  delete reinterpret_cast<Grammar*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    addRule
+ * Signature: (JJJ)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Grammar_addRule(JNIEnv* env,
+                                        jobject,
+                                        jlong pointer,
+                                        jlong ntSymbolPointer,
+                                        jlong rulePointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Grammar* current = reinterpret_cast<Grammar*>(pointer);
+  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
+  Term* rule = reinterpret_cast<Term*>(rulePointer);
+  current->addRule(*ntSymbol, *rule);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    addRules
+ * Signature: (JJ[J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Grammar_addRules(JNIEnv* env,
+                                         jobject,
+                                         jlong pointer,
+                                         jlong ntSymbolPointer,
+                                         jlongArray rulePointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Grammar* current = reinterpret_cast<Grammar*>(pointer);
+  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
+  std::vector<Term> rules = getObjectsFromPointers<Term>(env, rulePointers);
+  current->addRules(*ntSymbol, rules);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    addAnyConstant
+ * Signature: (JJ)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Grammar_addAnyConstant(
+    JNIEnv* env, jobject, jlong pointer, jlong ntSymbolPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Grammar* current = reinterpret_cast<Grammar*>(pointer);
+  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
+  current->addAnyConstant(*ntSymbol);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    addAnyVariable
+ * Signature: (JJ)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Grammar_addAnyVariable(
+    JNIEnv* env, jobject, jlong pointer, jlong ntSymbolPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Grammar* current = reinterpret_cast<Grammar*>(pointer);
+  Term* ntSymbol = reinterpret_cast<Term*>(ntSymbolPointer);
+  current->addAnyVariable(*ntSymbol);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Grammar
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Grammar_toString(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Grammar* current = reinterpret_cast<Grammar*>(pointer);
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/op.cpp b/src/api/java/jni/op.cpp
new file mode 100644 (file)
index 0000000..cb6a7a7
--- /dev/null
@@ -0,0 +1,199 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Op.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Op_deletePointer(JNIEnv*,
+                                                                jclass,
+                                                                jlong pointer)
+{
+  delete reinterpret_cast<Op*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    equals
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Op_equals(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer1,
+                                                             jlong pointer2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* op1 = reinterpret_cast<Op*>(pointer1);
+  Op* op2 = reinterpret_cast<Op*>(pointer2);
+  // We compare the actual operators, not their pointers.
+  return static_cast<jboolean>(*op1 == *op2);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    getKind
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Op_getKind(JNIEnv* env,
+                                                          jobject,
+                                                          jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  return static_cast<jboolean>(current->getKind());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Op_isNull(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  return static_cast<jboolean>(current->isNull());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    isIndexed
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Op_isIndexed(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  return static_cast<jboolean>(current->isIndexed());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    getNumIndices
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Op_getNumIndices(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  return static_cast<jint>(current->getNumIndices());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    getIntegerIndices
+ * Signature: (J)[I
+ */
+JNIEXPORT jintArray JNICALL Java_io_github_cvc5_api_Op_getIntegerIndices(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  size_t size = current->getNumIndices();
+  std::vector<jint> indices(size);
+  if (size == 1)
+  {
+    uint32_t index = current->getIndices<uint32_t>();
+    indices[0] = index;
+  }
+
+  if (size == 2)
+  {
+    std::pair<uint32_t, uint32_t> pair =
+        current->getIndices<std::pair<uint32_t, uint32_t>>();
+    indices[0] = pair.first;
+    indices[1] = pair.second;
+  }
+
+  if (size > 2)
+  {
+    std::string message = "Unhandled case when number of indices > 2.";
+    throw CVC5ApiException(message);
+  }
+
+  jintArray ret = env->NewIntArray((jsize)size);
+  env->SetIntArrayRegion(ret, 0, size, indices.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    getStringIndices
+ * Signature: (J)[Ljava/lang/String;
+ */
+JNIEXPORT jobjectArray JNICALL
+Java_io_github_cvc5_api_Op_getStringIndices(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  size_t size = current->getNumIndices();
+  std::vector<jstring> indices(size);
+  if (size == 1)
+  {
+    std::string cIndex = current->getIndices<std::string>();
+    jstring jIndex = env->NewStringUTF(cIndex.c_str());
+    indices[0] = jIndex;
+  }
+
+  if (size > 1)  // currently only one string is implemented in cvc5.cpp
+  {
+    std::string message = "Unhandled case when number of indices > 1.";
+    throw CVC5ApiException(message);
+  }
+
+  // construct a java array of String
+  jclass stringClass = env->FindClass("Ljava/lang/String;");
+  jobjectArray ret = env->NewObjectArray((jsize)size, stringClass, nullptr);
+  for (size_t i = 0; i < size; i++)
+  {
+    env->SetObjectArrayElement(ret, i, indices[i]);
+  }
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Op
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Op_toString(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* current = reinterpret_cast<Op*>(pointer);
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/option_Info.cpp b/src/api/java/jni/option_Info.cpp
new file mode 100644 (file)
index 0000000..4c60253
--- /dev/null
@@ -0,0 +1,345 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_OptionInfo.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_OptionInfo_deletePointer(JNIEnv*, jclass, jlong pointer)
+{
+  delete reinterpret_cast<OptionInfo*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_OptionInfo_toString(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::stringstream ss;
+  ss << *current;
+  return env->NewStringUTF(ss.str().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_OptionInfo_getName(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  return env->NewStringUTF(current->name.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getAliases
+ * Signature: (J)[Ljava/lang/String;
+ */
+JNIEXPORT jobjectArray JNICALL Java_io_github_cvc5_api_OptionInfo_getAliases(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  jobjectArray ret = getStringArrayFromStringVector(env, current->aliases);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getSetByUser
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_OptionInfo_getSetByUser(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  return static_cast<jboolean>(current->setByUser);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/**
+ * Convert OptionInfo::NumberInfo cpp object to OptionInfo.NumberInfo java
+ * object
+ * @tparam T cpp integer types int64_t, uint64_t, etc
+ * @param env jni environment
+ * @param optionInfo a java object for this OptionInfo
+ * @param numberInfoClass the java class for OptionInfo.NumberInfo
+ * @param methodId a constructor for OptionInfo.NumberInfo
+ * @param info the cpp OptionInfo::NumberInfo object
+ * @return a java object of class OptionInfo.NumberInfo<BigInteger>
+ */
+template <typename T>
+jobject getNumberInfoFromInteger(JNIEnv* env,
+                                 const _jobject* optionInfo,
+                                 jclass numberInfoClass,
+                                 jmethodID methodId,
+                                 const OptionInfo::NumberInfo<T>& info)
+{
+  jobject defaultValue = getBigIntegerObject<T>(env, info.defaultValue);
+  jobject currentValue = getBigIntegerObject<T>(env, info.currentValue);
+  jobject minimum = nullptr;
+  if (info.minimum)
+  {
+    minimum = getBigIntegerObject<T>(env, *info.minimum);
+  }
+  jobject maximum = nullptr;
+  if (info.maximum)
+  {
+    maximum = getBigIntegerObject<T>(env, *info.maximum);
+  }
+  jobject ret = env->NewObject(numberInfoClass,
+                               methodId,
+                               optionInfo,
+                               defaultValue,
+                               currentValue,
+                               minimum,
+                               maximum);
+
+  return ret;
+}
+
+template <typename T>
+jobject getNumberInfoFromInteger(JNIEnv* env,
+                                 const _jobject* optionInfo,
+                                 jclass numberInfoClass,
+                                 jmethodID methodId,
+                                 const OptionInfo::NumberInfo<int64_t>& info);
+
+template <typename T>
+jobject getNumberInfoFromInteger(JNIEnv* env,
+                                 const _jobject* optionInfo,
+                                 jclass numberInfoClass,
+                                 jmethodID methodId,
+                                 const OptionInfo::NumberInfo<uint64_t>& info);
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getBaseInfo
+ * Signature: (J)Lio/github/cvc5/api/BaseInfo;
+ */
+JNIEXPORT jobject JNICALL Java_io_github_cvc5_api_OptionInfo_getBaseInfo(
+    JNIEnv* env, jobject optionInfo, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::variant<OptionInfo::VoidInfo,
+               OptionInfo::ValueInfo<bool>,
+               OptionInfo::ValueInfo<std::string>,
+               OptionInfo::NumberInfo<int64_t>,
+               OptionInfo::NumberInfo<uint64_t>,
+               OptionInfo::NumberInfo<double>,
+               OptionInfo::ModeInfo>
+      v = current->valueInfo;
+
+  if (std::holds_alternative<OptionInfo::VoidInfo>(v))
+  {
+    jclass voidInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$VoidInfo");
+    jmethodID methodId = env->GetMethodID(
+        voidInfoClass, "<init>", "(Lio/github/cvc5/api/OptionInfo;)V");
+    jobject ret = env->NewObject(voidInfoClass, methodId, optionInfo);
+    return ret;
+  }
+
+  if (std::holds_alternative<OptionInfo::ValueInfo<bool>>(v)
+      || std::holds_alternative<OptionInfo::ValueInfo<std::string>>(v))
+  {
+    jclass valueInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$ValueInfo");
+    jmethodID methodId =
+        env->GetMethodID(valueInfoClass,
+                         "<init>",
+                         "(Lio/github/cvc5/api/OptionInfo;Ljava/lang/"
+                         "Object;Ljava/lang/Object;)V");
+
+    if (std::holds_alternative<OptionInfo::ValueInfo<bool>>(v))
+    {
+      auto info = std::get<OptionInfo::ValueInfo<bool>>(v);
+      jobject currentValue = getBooleanObject(env, info.currentValue);
+      jobject defaultValue = getBooleanObject(env, info.defaultValue);
+      jobject ret = env->NewObject(
+          valueInfoClass, methodId, optionInfo, defaultValue, currentValue);
+      return ret;
+    }
+
+    if (std::holds_alternative<OptionInfo::ValueInfo<std::string>>(v))
+    {
+      auto info = std::get<OptionInfo::ValueInfo<std::string>>(v);
+      jstring defaultValue = env->NewStringUTF(info.defaultValue.c_str());
+      jstring currentValue = env->NewStringUTF(info.currentValue.c_str());
+      jobject ret = env->NewObject(
+          valueInfoClass, methodId, optionInfo, defaultValue, currentValue);
+      return ret;
+    }
+  }
+
+  if (std::holds_alternative<OptionInfo::NumberInfo<int64_t>>(v)
+      || std::holds_alternative<OptionInfo::NumberInfo<uint64_t>>(v)
+      || std::holds_alternative<OptionInfo::NumberInfo<double>>(v))
+  {
+    jclass numberInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$NumberInfo");
+    jmethodID methodId = env->GetMethodID(
+        numberInfoClass,
+        "<init>",
+        "(Lio/github/cvc5/api/OptionInfo;Ljava/lang/Object;Ljava/lang/"
+        "Object;Ljava/lang/Object;Ljava/lang/Object;)V");
+
+    if (std::holds_alternative<OptionInfo::NumberInfo<int64_t>>(v))
+    {
+      auto info = std::get<OptionInfo::NumberInfo<int64_t>>(v);
+      return getNumberInfoFromInteger(
+          env, optionInfo, numberInfoClass, methodId, info);
+    }
+
+    if (std::holds_alternative<OptionInfo::NumberInfo<uint64_t>>(v))
+    {
+      auto info = std::get<OptionInfo::NumberInfo<uint64_t>>(v);
+      return getNumberInfoFromInteger(
+          env, optionInfo, numberInfoClass, methodId, info);
+    }
+
+    if (std::holds_alternative<OptionInfo::NumberInfo<double>>(v))
+    {
+      auto info = std::get<OptionInfo::NumberInfo<double>>(v);
+      jobject defaultValue = getDoubleObject(env, info.defaultValue);
+      jobject currentValue = getDoubleObject(env, info.currentValue);
+      jobject minimum = nullptr;
+      if (info.minimum)
+      {
+        minimum = getDoubleObject(env, *info.minimum);
+      }
+      jobject maximum = nullptr;
+      if (info.maximum)
+      {
+        maximum = getDoubleObject(env, *info.maximum);
+      }
+      jobject ret = env->NewObject(numberInfoClass,
+                                   methodId,
+                                   optionInfo,
+                                   defaultValue,
+                                   currentValue,
+                                   minimum,
+                                   maximum);
+      return ret;
+    }
+  }
+
+  if (std::holds_alternative<OptionInfo::ModeInfo>(v))
+  {
+    jclass modeInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$ModeInfo");
+    jmethodID methodId = env->GetMethodID(
+        modeInfoClass,
+        "<init>",
+        "(Lio/github/cvc5/api/OptionInfo;Ljava/lang/String;Ljava/lang/"
+        "String;[Ljava/lang/String;)V");
+
+    auto info = std::get<OptionInfo::ModeInfo>(v);
+    jstring defaultValue = env->NewStringUTF(info.defaultValue.c_str());
+    jstring currentValue = env->NewStringUTF(info.currentValue.c_str());
+    jobject stringArray = getStringArrayFromStringVector(env, info.modes);
+    jobject ret = env->NewObject(modeInfoClass,
+                                 methodId,
+                                 optionInfo,
+                                 defaultValue,
+                                 currentValue,
+                                 stringArray);
+    return ret;
+  }
+
+  return nullptr;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    booleanValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_OptionInfo_booleanValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  return static_cast<jboolean>(current->boolValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    stringValue
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_OptionInfo_stringValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::string ret = current->stringValue();
+  return env->NewStringUTF(ret.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    intValue
+ * Signature: (J)Ljava/math/BigInteger;
+ */
+JNIEXPORT jobject JNICALL
+Java_io_github_cvc5_api_OptionInfo_intValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::int64_t value = current->intValue();
+  jobject ret = getBigIntegerObject<std::int64_t>(env, value);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    doubleValue
+ * Signature: (J)D
+ */
+JNIEXPORT jdouble JNICALL Java_io_github_cvc5_api_OptionInfo_doubleValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  double ret = current->doubleValue();
+  return static_cast<jdouble>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jdouble>(0.0));
+}
diff --git a/src/api/java/jni/option_info.cpp b/src/api/java/jni/option_info.cpp
new file mode 100644 (file)
index 0000000..031b1ba
--- /dev/null
@@ -0,0 +1,345 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_OptionInfo.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_OptionInfo_deletePointer(JNIEnv*, jclass, jlong pointer)
+{
+  delete reinterpret_cast<OptionInfo*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_OptionInfo_toString(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::stringstream ss;
+  ss << *current;
+  return env->NewStringUTF(ss.str().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_OptionInfo_getName(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  return env->NewStringUTF(current->name.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getAliases
+ * Signature: (J)[Ljava/lang/String;
+ */
+JNIEXPORT jobjectArray JNICALL Java_io_github_cvc5_api_OptionInfo_getAliases(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  jobjectArray ret = getStringArrayFromStringVector(env, current->aliases);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getSetByUser
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_OptionInfo_getSetByUser(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  return static_cast<jboolean>(current->setByUser);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/**
+ * Convert OptionInfo::NumberInfo cpp object to OptionInfo.NumberInfo java
+ * object
+ * @tparam T cpp integer types int64_t, uint64_t, etc
+ * @param env jni environment
+ * @param optionInfo a java object for this OptionInfo
+ * @param numberInfoClass the java class for OptionInfo.NumberInfo
+ * @param methodId a constructor for OptionInfo.NumberInfo
+ * @param info the cpp OptionInfo::NumberInfo object
+ * @return a java object of class OptionInfo.NumberInfo<BigInteger>
+ */
+template <typename T>
+jobject getNumberInfoFromInteger(JNIEnv* env,
+                                 const _jobject* optionInfo,
+                                 jclass numberInfoClass,
+                                 jmethodID methodId,
+                                 const OptionInfo::NumberInfo<T>& info)
+{
+  jobject defaultValue = getBigIntegerObject<T>(env, info.defaultValue);
+  jobject currentValue = getBigIntegerObject<T>(env, info.currentValue);
+  jobject minimum = nullptr;
+  if (info.minimum)
+  {
+    minimum = getBigIntegerObject<T>(env, *info.minimum);
+  }
+  jobject maximum = nullptr;
+  if (info.maximum)
+  {
+    maximum = getBigIntegerObject<T>(env, *info.maximum);
+  }
+  jobject ret = env->NewObject(numberInfoClass,
+                               methodId,
+                               optionInfo,
+                               defaultValue,
+                               currentValue,
+                               minimum,
+                               maximum);
+
+  return ret;
+}
+
+template <typename T>
+jobject getNumberInfoFromInteger(JNIEnv* env,
+                                 const _jobject* optionInfo,
+                                 jclass numberInfoClass,
+                                 jmethodID methodId,
+                                 const OptionInfo::NumberInfo<int64_t>& info);
+
+template <typename T>
+jobject getNumberInfoFromInteger(JNIEnv* env,
+                                 const _jobject* optionInfo,
+                                 jclass numberInfoClass,
+                                 jmethodID methodId,
+                                 const OptionInfo::NumberInfo<uint64_t>& info);
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    getBaseInfo
+ * Signature: (J)Lio/github/cvc5/api/OptionInfo/BaseInfo;
+ */
+JNIEXPORT jobject JNICALL Java_io_github_cvc5_api_OptionInfo_getBaseInfo(
+    JNIEnv* env, jobject optionInfo, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::variant<OptionInfo::VoidInfo,
+               OptionInfo::ValueInfo<bool>,
+               OptionInfo::ValueInfo<std::string>,
+               OptionInfo::NumberInfo<int64_t>,
+               OptionInfo::NumberInfo<uint64_t>,
+               OptionInfo::NumberInfo<double>,
+               OptionInfo::ModeInfo>
+      v = current->valueInfo;
+
+  if (std::holds_alternative<OptionInfo::VoidInfo>(v))
+  {
+    jclass voidInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$VoidInfo");
+    jmethodID methodId = env->GetMethodID(
+        voidInfoClass, "<init>", "(Lio/github/cvc5/api/OptionInfo;)V");
+    jobject ret = env->NewObject(voidInfoClass, methodId, optionInfo);
+    return ret;
+  }
+
+  if (std::holds_alternative<OptionInfo::ValueInfo<bool>>(v)
+      || std::holds_alternative<OptionInfo::ValueInfo<std::string>>(v))
+  {
+    jclass valueInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$ValueInfo");
+    jmethodID methodId =
+        env->GetMethodID(valueInfoClass,
+                         "<init>",
+                         "(Lio/github/cvc5/api/OptionInfo;Ljava/lang/"
+                         "Object;Ljava/lang/Object;)V");
+
+    if (std::holds_alternative<OptionInfo::ValueInfo<bool>>(v))
+    {
+      auto info = std::get<OptionInfo::ValueInfo<bool>>(v);
+      jobject currentValue = getBooleanObject(env, info.currentValue);
+      jobject defaultValue = getBooleanObject(env, info.defaultValue);
+      jobject ret = env->NewObject(
+          valueInfoClass, methodId, optionInfo, defaultValue, currentValue);
+      return ret;
+    }
+
+    if (std::holds_alternative<OptionInfo::ValueInfo<std::string>>(v))
+    {
+      auto info = std::get<OptionInfo::ValueInfo<std::string>>(v);
+      jstring defaultValue = env->NewStringUTF(info.defaultValue.c_str());
+      jstring currentValue = env->NewStringUTF(info.currentValue.c_str());
+      jobject ret = env->NewObject(
+          valueInfoClass, methodId, optionInfo, defaultValue, currentValue);
+      return ret;
+    }
+  }
+
+  if (std::holds_alternative<OptionInfo::NumberInfo<int64_t>>(v)
+      || std::holds_alternative<OptionInfo::NumberInfo<uint64_t>>(v)
+      || std::holds_alternative<OptionInfo::NumberInfo<double>>(v))
+  {
+    jclass numberInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$NumberInfo");
+    jmethodID methodId = env->GetMethodID(
+        numberInfoClass,
+        "<init>",
+        "(Lio/github/cvc5/api/OptionInfo;Ljava/lang/Object;Ljava/lang/"
+        "Object;Ljava/lang/Object;Ljava/lang/Object;)V");
+
+    if (std::holds_alternative<OptionInfo::NumberInfo<int64_t>>(v))
+    {
+      auto info = std::get<OptionInfo::NumberInfo<int64_t>>(v);
+      return getNumberInfoFromInteger(
+          env, optionInfo, numberInfoClass, methodId, info);
+    }
+
+    if (std::holds_alternative<OptionInfo::NumberInfo<uint64_t>>(v))
+    {
+      auto info = std::get<OptionInfo::NumberInfo<uint64_t>>(v);
+      return getNumberInfoFromInteger(
+          env, optionInfo, numberInfoClass, methodId, info);
+    }
+
+    if (std::holds_alternative<OptionInfo::NumberInfo<double>>(v))
+    {
+      auto info = std::get<OptionInfo::NumberInfo<double>>(v);
+      jobject defaultValue = getDoubleObject(env, info.defaultValue);
+      jobject currentValue = getDoubleObject(env, info.currentValue);
+      jobject minimum = nullptr;
+      if (info.minimum)
+      {
+        minimum = getDoubleObject(env, *info.minimum);
+      }
+      jobject maximum = nullptr;
+      if (info.maximum)
+      {
+        maximum = getDoubleObject(env, *info.maximum);
+      }
+      jobject ret = env->NewObject(numberInfoClass,
+                                   methodId,
+                                   optionInfo,
+                                   defaultValue,
+                                   currentValue,
+                                   minimum,
+                                   maximum);
+      return ret;
+    }
+  }
+
+  if (std::holds_alternative<OptionInfo::ModeInfo>(v))
+  {
+    jclass modeInfoClass =
+        env->FindClass("io/github/cvc5/api/OptionInfo$ModeInfo");
+    jmethodID methodId = env->GetMethodID(
+        modeInfoClass,
+        "<init>",
+        "(Lio/github/cvc5/api/OptionInfo;Ljava/lang/String;Ljava/lang/"
+        "String;[Ljava/lang/String;)V");
+
+    auto info = std::get<OptionInfo::ModeInfo>(v);
+    jstring defaultValue = env->NewStringUTF(info.defaultValue.c_str());
+    jstring currentValue = env->NewStringUTF(info.currentValue.c_str());
+    jobject stringArray = getStringArrayFromStringVector(env, info.modes);
+    jobject ret = env->NewObject(modeInfoClass,
+                                 methodId,
+                                 optionInfo,
+                                 defaultValue,
+                                 currentValue,
+                                 stringArray);
+    return ret;
+  }
+
+  return nullptr;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    booleanValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_OptionInfo_booleanValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  return static_cast<jboolean>(current->boolValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    stringValue
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_OptionInfo_stringValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::string ret = current->stringValue();
+  return env->NewStringUTF(ret.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    intValue
+ * Signature: (J)Ljava/math/BigInteger;
+ */
+JNIEXPORT jobject JNICALL
+Java_io_github_cvc5_api_OptionInfo_intValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  std::int64_t value = current->intValue();
+  jobject ret = getBigIntegerObject<std::int64_t>(env, value);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_OptionInfo
+ * Method:    doubleValue
+ * Signature: (J)D
+ */
+JNIEXPORT jdouble JNICALL Java_io_github_cvc5_api_OptionInfo_doubleValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  OptionInfo* current = reinterpret_cast<OptionInfo*>(pointer);
+  double ret = current->doubleValue();
+  return static_cast<jdouble>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jdouble>(0.0));
+}
diff --git a/src/api/java/jni/result.cpp b/src/api/java/jni/result.cpp
new file mode 100644 (file)
index 0000000..34b3262
--- /dev/null
@@ -0,0 +1,179 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Result.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Result_deletePointer(JNIEnv*, jclass, jlong pointer)
+{
+  delete ((Result*)pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Result_isNull(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isNull();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isSat
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Result_isSat(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isSat();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isUnsat
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Result_isUnsat(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isUnsat();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isSatUnknown
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Result_isSatUnknown(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isSatUnknown();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isEntailed
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Result_isEntailed(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isEntailed();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isNotEntailed
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Result_isNotEntailed(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isNotEntailed();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    isEntailmentUnknown
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Result_isEntailmentUnknown(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jboolean)current->isEntailmentUnknown();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    equals
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Result_equals(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer1,
+                                                                 jlong pointer2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* result1 = (Result*)pointer1;
+  Result* result2 = (Result*)pointer2;
+  // We compare the actual terms, not their pointers.
+  return (jboolean)(*result1 == *result2);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, (jboolean) false);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    getUnknownExplanation
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Result_getUnknownExplanation(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return (jint)current->getUnknownExplanation();
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Result
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Result_toString(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* current = (Result*)pointer;
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/solver.cpp b/src/api/java/jni/solver.cpp
new file mode 100644 (file)
index 0000000..882a747
--- /dev/null
@@ -0,0 +1,2710 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Solver.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    newSolver
+ * Signature: ()J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_newSolver(JNIEnv*,
+                                                                 jobject)
+{
+  Solver* solver = new Solver();
+  return reinterpret_cast<jlong>(solver);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Solver_deletePointer(JNIEnv*, jclass, jlong pointer)
+{
+  delete (reinterpret_cast<Solver*>(pointer));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getNullSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_getNullSort(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getNullSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getBooleanSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getBooleanSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getBooleanSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getIntegerSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getIntegerSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getIntegerSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getRealSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_getRealSort(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getRealSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getRegExpSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getRegExpSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getRegExpSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getRoundingModeSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getRoundingModeSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getRoundingModeSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getStringSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getStringSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->getStringSort());
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkArraySort
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkArraySort(JNIEnv* env,
+                                           jobject,
+                                           jlong pointer,
+                                           jlong indexSortPointer,
+                                           jlong elementSortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* indexSort = reinterpret_cast<Sort*>(indexSortPointer);
+  Sort* elementSort = reinterpret_cast<Sort*>(elementSortPointer);
+  Sort* retPointer = new Sort(solver->mkArraySort(*indexSort, *elementSort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkBitVectorSort
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkBitVectorSort(
+    JNIEnv* env, jobject, jlong pointer, jint size)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer = new Sort(solver->mkBitVectorSort((uint32_t)size));
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkFloatingPointSort
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkFloatingPointSort(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sortPointer =
+      new Sort(solver->mkFloatingPointSort((uint32_t)exp, (uint32_t)sig));
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeSort
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkDatatypeSort(
+    JNIEnv* env, jobject, jlong pointer, jlong datatypeDeclPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  DatatypeDecl* decl = reinterpret_cast<DatatypeDecl*>(datatypeDeclPointer);
+  Sort* retPointer = new Sort(solver->mkDatatypeSort(*decl));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeSorts
+ * Signature: (J[J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Solver_mkDatatypeSorts__J_3J(JNIEnv* env,
+                                                     jobject,
+                                                     jlong pointer,
+                                                     jlongArray jDecls)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<DatatypeDecl> decls =
+      getObjectsFromPointers<DatatypeDecl>(env, jDecls);
+  std::vector<Sort> sorts = solver->mkDatatypeSorts(decls);
+  std::vector<jlong> sortPointers(sorts.size());
+
+  for (size_t i = 0; i < sorts.size(); i++)
+  {
+    sortPointers[i] = reinterpret_cast<jlong>(new Sort(sorts[i]));
+  }
+
+  jlongArray ret = env->NewLongArray(sorts.size());
+  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeSorts
+ * Signature: (J[J[J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Solver_mkDatatypeSorts__J_3J_3J(JNIEnv* env,
+                                                        jobject,
+                                                        jlong pointer,
+                                                        jlongArray jDecls,
+                                                        jlongArray jUnresolved)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<DatatypeDecl> decls =
+      getObjectsFromPointers<DatatypeDecl>(env, jDecls);
+  std::vector<Sort> cUnresolved =
+      getObjectsFromPointers<Sort>(env, jUnresolved);
+  std::set<Sort> unresolved(cUnresolved.begin(), cUnresolved.end());
+  std::vector<Sort> sorts = solver->mkDatatypeSorts(decls, unresolved);
+  jlongArray ret = getPointersFromObjects<Sort>(env, sorts);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkFunctionSort
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkFunctionSort__JJJ(JNIEnv* env,
+                                                   jobject,
+                                                   jlong pointer,
+                                                   jlong domainPointer,
+                                                   jlong codomainPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* domain = reinterpret_cast<Sort*>(domainPointer);
+  Sort* codomain = reinterpret_cast<Sort*>(codomainPointer);
+  Sort* sortPointer = new Sort(solver->mkFunctionSort(*domain, *codomain));
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkFunctionSort
+ * Signature: (J[JJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkFunctionSort__J_3JJ(JNIEnv* env,
+                                                     jobject,
+                                                     jlong pointer,
+                                                     jlongArray sortPointers,
+                                                     jlong codomainPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* codomain = reinterpret_cast<Sort*>(codomainPointer);
+  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
+  Sort* retPointer = new Sort(solver->mkFunctionSort(sorts, *codomain));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkParamSort
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkParamSort(
+    JNIEnv* env, jobject, jlong pointer, jstring jSymbol)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  Sort* retPointer = new Sort(solver->mkParamSort(cSymbol));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkPredicateSort
+ * Signature: (J[J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkPredicateSort(
+    JNIEnv* env, jobject, jlong pointer, jlongArray sortPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
+  Sort* retPointer = new Sort(solver->mkPredicateSort(sorts));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkRecordSort
+ * Signature: (J[Lio/github/cvc5/api/Pair;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkRecordSort(
+    JNIEnv* env, jobject, jlong pointer, jobjectArray jFields)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  jsize size = env->GetArrayLength(jFields);
+  // Lio/github/cvc5/api/Pair; is signature of cvc5.Pair<String, Long>
+  jclass pairClass = env->FindClass("Lio/github/cvc5/api/Pair;");
+  jclass longClass = env->FindClass("Ljava/lang/Long;");
+  // Ljava/lang/Object; is the signature of cvc5.Pair.first field
+  jfieldID firstFieldId =
+      env->GetFieldID(pairClass, "first", "Ljava/lang/Object;");
+  // Ljava/lang/Object; is the signature of cvc5.Pair.second field
+  jfieldID secondFieldId =
+      env->GetFieldID(pairClass, "second", "Ljava/lang/Object;");
+  // we need to call method longValue to get long Long object
+  jmethodID methodId = env->GetMethodID(longClass, "longValue", "()J");
+
+  std::vector<std::pair<std::string, Sort>> cFields;
+  for (jsize i = 0; i < size; i++)
+  {
+    // get the pair at index i
+    jobject object = env->GetObjectArrayElement(jFields, i);
+
+    // get the object at cvc5.Pair.first and convert it to char *
+    jstring jFirst = (jstring)env->GetObjectField(object, firstFieldId);
+    const char* cFirst = env->GetStringUTFChars(jFirst, nullptr);
+
+    // get the object at cvc5.Pair.second and convert it to Sort
+    jobject jSecond = env->GetObjectField(object, secondFieldId);
+    jlong sortPointer = env->CallLongMethod(jSecond, methodId);
+    Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+
+    // add the pair to to the list of fields
+    cFields.push_back(std::make_pair(std::string(cFirst), *sort));
+  }
+  // get the record sort from the solver
+  Sort* retPointer = new Sort(solver->mkRecordSort(cFields));
+  // return a pointer to the sort
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSetSort
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkSetSort(
+    JNIEnv* env, jobject, jlong pointer, jlong elemSortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* elemSort = reinterpret_cast<Sort*>(elemSortPointer);
+  Sort* retPointer = new Sort(solver->mkSetSort(*elemSort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkBagSort
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkBagSort(
+    JNIEnv* env, jobject, jlong pointer, jlong elemSortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* elemSort = reinterpret_cast<Sort*>(elemSortPointer);
+  Sort* retPointer = new Sort(solver->mkBagSort(*elemSort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSequenceSort
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkSequenceSort(
+    JNIEnv* env, jobject, jlong pointer, jlong elemSortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* elemSort = reinterpret_cast<Sort*>(elemSortPointer);
+  Sort* sortPointer = new Sort(solver->mkSequenceSort(*elemSort));
+  return reinterpret_cast<jlong>(sortPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkUninterpretedSort
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkUninterpretedSort(
+    JNIEnv* env, jobject, jlong pointer, jstring jSymbol)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* cSymbol = env->GetStringUTFChars(jSymbol, nullptr);
+  Sort* sort = new Sort(solver->mkUninterpretedSort(std::string(cSymbol)));
+  env->ReleaseStringUTFChars(jSymbol, cSymbol);
+  return reinterpret_cast<jlong>(sort);
+
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSortConstructorSort
+ * Signature: (JLjava/lang/String;I)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkSortConstructorSort(
+    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jint arity)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  Sort* retPointer =
+      new Sort(solver->mkSortConstructorSort(cSymbol, (size_t)arity));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTupleSort
+ * Signature: (J[J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkTupleSort(
+    JNIEnv* env, jobject, jlong pointer, jlongArray sortPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
+  Sort* retPointer = new Sort(solver->mkTupleSort(sorts));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkTerm__JI(
+    JNIEnv* env, jobject, jlong pointer, jint kindValue)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Term* retPointer = new Term(solver->mkTerm(kind));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JIJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkTerm__JIJ(
+    JNIEnv* env, jobject, jlong pointer, jint kindValue, jlong childPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Term* child = reinterpret_cast<Term*>(childPointer);
+  Term* termPointer = new Term(solver->mkTerm(kind, *child));
+  return reinterpret_cast<jlong>(termPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JIJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTerm__JIJJ(JNIEnv* env,
+                                            jobject,
+                                            jlong pointer,
+                                            jint kindValue,
+                                            jlong child1Pointer,
+                                            jlong child2Pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
+  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
+  Term* termPointer = new Term(solver->mkTerm(kind, *child1, *child2));
+  return reinterpret_cast<jlong>(termPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JIJJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTerm__JIJJJ(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jint kindValue,
+                                             jlong child1Pointer,
+                                             jlong child2Pointer,
+                                             jlong child3Pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
+  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
+  Term* child3 = reinterpret_cast<Term*>(child3Pointer);
+  Term* retPointer = new Term(solver->mkTerm(kind, *child1, *child2, *child3));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JI[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTerm__JI_3J(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jint kindValue,
+                                             jlongArray childrenPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  std::vector<Term> children =
+      getObjectsFromPointers<Term>(env, childrenPointers);
+  Term* retPointer = new Term(solver->mkTerm(kind, children));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkTerm__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong opPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Op* op = reinterpret_cast<Op*>(opPointer);
+  Term* retPointer = new Term(solver->mkTerm(*op));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkTerm__JJJ(
+    JNIEnv* env, jobject, jlong pointer, jlong opPointer, jlong childPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Op* op = reinterpret_cast<Op*>(opPointer);
+  Term* child = reinterpret_cast<Term*>(childPointer);
+  Term* retPointer = new Term(solver->mkTerm(*op, *child));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JJJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTerm__JJJJ(JNIEnv* env,
+                                            jobject,
+                                            jlong pointer,
+                                            jlong opPointer,
+                                            jlong child1Pointer,
+                                            jlong child2Pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Op* op = reinterpret_cast<Op*>(opPointer);
+  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
+  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
+  Term* retPointer = new Term(solver->mkTerm(*op, *child1, *child2));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JJJJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTerm__JJJJJ(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jlong opPointer,
+                                             jlong child1Pointer,
+                                             jlong child2Pointer,
+                                             jlong child3Pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Op* op = reinterpret_cast<Op*>(opPointer);
+  Term* child1 = reinterpret_cast<Term*>(child1Pointer);
+  Term* child2 = reinterpret_cast<Term*>(child2Pointer);
+  Term* child3 = reinterpret_cast<Term*>(child3Pointer);
+  Term* retPointer = new Term(solver->mkTerm(*op, *child1, *child2, *child3));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTerm
+ * Signature: (JJ[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTerm__JJ_3J(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jlong opPointer,
+                                             jlongArray childrenPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Op* op = reinterpret_cast<Op*>(opPointer);
+  std::vector<Term> children =
+      getObjectsFromPointers<Term>(env, childrenPointers);
+  Term* retPointer = new Term(solver->mkTerm(*op, children));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTuple
+ * Signature: (J[J[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkTuple(JNIEnv* env,
+                                       jobject,
+                                       jlong pointer,
+                                       jlongArray sortPointers,
+                                       jlongArray termPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
+  std::vector<Term> terms = getObjectsFromPointers<Term>(env, termPointers);
+  Term* retPointer = new Term(solver->mkTuple(sorts, terms));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkOp
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkOp__JI(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer,
+                                                                jint kindValue)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Op* retPointer = new Op(solver->mkOp(kind));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkOp
+ * Signature: (JILjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkOp__JILjava_lang_String_2(
+    JNIEnv* env, jobject, jlong pointer, jint kindValue, jstring jArg)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  const char* s = env->GetStringUTFChars(jArg, nullptr);
+  std::string cArg(s);
+
+  Op* retPointer = new Op(solver->mkOp(kind, cArg));
+
+  env->ReleaseStringUTFChars(jArg, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkOp
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkOp__JII(
+    JNIEnv* env, jobject, jlong pointer, jint kindValue, jint arg)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Op* retPointer = new Op(solver->mkOp(kind, (uint32_t)arg));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkOp
+ * Signature: (JIII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkOp__JIII(
+    JNIEnv* env, jobject, jlong pointer, jint kindValue, jint arg1, jint arg2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+  Op* retPointer = new Op(solver->mkOp(kind, (uint32_t)arg1, (uint32_t)arg2));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkOp
+ * Signature: (JI[I)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkOp__JI_3I(
+    JNIEnv* env, jobject, jlong pointer, jint kindValue, jintArray jArgs)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Kind kind = (Kind)kindValue;
+
+  jsize size = env->GetArrayLength(jArgs);
+  jint* argElements = env->GetIntArrayElements(jArgs, nullptr);
+
+  std::vector<uint32_t> cArgs(size);
+  for (jsize i = 0; i < size; i++)
+  {
+    cArgs[i] = (uint32_t)argElements[i];
+  }
+  env->ReleaseIntArrayElements(jArgs, argElements, 0);
+
+  Op* retPointer = new Op(solver->mkOp(kind, cArgs));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkTrue
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkTrue(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* termPointer = new Term(solver->mkTrue());
+  return reinterpret_cast<jlong>(termPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkFalse
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkFalse(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* termPointer = new Term(solver->mkFalse());
+  return reinterpret_cast<jlong>(termPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkBoolean
+ * Signature: (JZ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkBoolean(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer,
+                                                                 jboolean val)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkBoolean((bool)val));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkPi
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkPi(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkPi());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkInteger
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkInteger__JLjava_lang_String_2(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer,
+                                                               jstring jS)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jS, nullptr);
+  std::string cS(s);
+  Term* retPointer = new Term(solver->mkInteger(cS));
+  env->ReleaseStringUTFChars(jS, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkInteger
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkInteger__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong val)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* termPointer = new Term(solver->mkInteger((int64_t)val));
+  return reinterpret_cast<jlong>(termPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkReal
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkReal__JLjava_lang_String_2(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer,
+                                                            jstring jS)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jS, nullptr);
+  std::string cS(s);
+  Term* retPointer = new Term(solver->mkReal(cS));
+  env->ReleaseStringUTFChars(jS, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkRealValue
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkRealValue(
+    JNIEnv* env, jobject, jlong pointer, jlong val)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkReal((int64_t)val));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkReal
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkReal__JJJ(
+    JNIEnv* env, jobject, jlong pointer, jlong num, jlong den)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkReal((int64_t)num, (int64_t)den));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkRegexpEmpty
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkRegexpEmpty(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkRegexpEmpty());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkRegexpSigma
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkRegexpSigma(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkRegexpSigma());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkEmptySet
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkEmptySet(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->mkEmptySet(*sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkEmptyBag
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkEmptyBag(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->mkEmptyBag(*sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSepEmp
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkSepEmp(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkSepEmp());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSepNil
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkSepNil(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->mkSepNil(*sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkString
+ * Signature: (JLjava/lang/String;Z)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkString__JLjava_lang_String_2Z(
+    JNIEnv* env, jobject, jlong pointer, jstring jS, jboolean useEscSequences)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jS, nullptr);
+  std::string cS(s);
+  Term* retPointer = new Term(solver->mkString(cS, (bool)useEscSequences));
+  env->ReleaseStringUTFChars(jS, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkEmptySequence
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkEmptySequence(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->mkEmptySequence(*sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkUniverseSet
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkUniverseSet(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->mkUniverseSet(*sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkBitVector
+ * Signature: (JIJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkBitVector__JIJ(
+    JNIEnv* env, jobject, jlong pointer, jint size, jlong val)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer =
+      new Term(solver->mkBitVector((uint32_t)size, (uint64_t)val));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkBitVector
+ * Signature: (JILjava/lang/String;I)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkBitVector__JILjava_lang_String_2I(
+    JNIEnv* env, jobject, jlong pointer, jint size, jstring jS, jint base)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jS, nullptr);
+  std::string cS(s);
+  Term* retPointer =
+      new Term(solver->mkBitVector((uint32_t)size, cS, (uint32_t)base));
+  env->ReleaseStringUTFChars(jS, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkConstArray
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkConstArray(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jlong valPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* val = reinterpret_cast<Term*>(valPointer);
+  Term* retPointer = new Term(solver->mkConstArray(*sort, *val));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkPosInf
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkPosInf(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkPosInf((uint32_t)exp, (uint32_t)sig));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkNegInf
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkNegInf(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkNegInf((uint32_t)exp, (uint32_t)sig));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkNaN
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkNaN(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkNaN((uint32_t)exp, (uint32_t)sig));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkPosZero
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkPosZero(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkPosZero((uint32_t)exp, (uint32_t)sig));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkNegZero
+ * Signature: (JII)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkNegZero(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkNegZero((uint32_t)exp, (uint32_t)sig));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkRoundingMode
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkRoundingMode(
+    JNIEnv* env, jobject, jlong pointer, jint rm)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkRoundingMode((RoundingMode)rm));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkUninterpretedConst
+ * Signature: (JJI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkUninterpretedConst(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jint index)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer =
+      new Term(solver->mkUninterpretedConst(*sort, (int32_t)index));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkAbstractValue
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkAbstractValue__JLjava_lang_String_2(
+    JNIEnv* env, jobject, jlong pointer, jstring jIndex)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jIndex, nullptr);
+  std::string cIndex(s);
+  Term* retPointer = new Term(solver->mkAbstractValue(cIndex));
+  env->ReleaseStringUTFChars(jIndex, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkAbstractValue
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkAbstractValue__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong index)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->mkAbstractValue((uint64_t)index));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkFloatingPoint
+ * Signature: (JIIJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkFloatingPoint(
+    JNIEnv* env, jobject, jlong pointer, jint exp, jint sig, jlong valPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* val = reinterpret_cast<Term*>(valPointer);
+  Term* retPointer =
+      new Term(solver->mkFloatingPoint((uint32_t)exp, (uint32_t)sig, *val));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkConst
+ * Signature: (JJLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkConst__JJLjava_lang_String_2(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jstring jSymbol)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  Term* retPointer = new Term(solver->mkConst(*sort, cSymbol));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkConst
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkConst__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->mkConst(*sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkVar
+ * Signature: (JJLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkVar(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jstring jSymbol)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  Term* ret = new Term(solver->mkVar(*sort, cSymbol));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeConstructorDecl
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkDatatypeConstructorDecl(JNIEnv* env,
+                                                         jobject,
+                                                         jlong pointer,
+                                                         jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+
+  DatatypeConstructorDecl* retPointer =
+      new DatatypeConstructorDecl(solver->mkDatatypeConstructorDecl(cName));
+  env->ReleaseStringUTFChars(jName, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeDecl
+ * Signature: (JLjava/lang/String;Z)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkDatatypeDecl__JLjava_lang_String_2Z(
+    JNIEnv* env, jobject, jlong pointer, jstring jName, jboolean isCoDatatype)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  DatatypeDecl* retPointer =
+      new DatatypeDecl(solver->mkDatatypeDecl(cName, (bool)isCoDatatype));
+  env->ReleaseStringUTFChars(jName, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeDecl
+ * Signature: (JLjava/lang/String;JZ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkDatatypeDecl__JLjava_lang_String_2JZ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jName,
+    jlong paramPointer,
+    jboolean isCoDatatype)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  Sort* param = reinterpret_cast<Sort*>(paramPointer);
+  DatatypeDecl* retPointer = new DatatypeDecl(
+      solver->mkDatatypeDecl(cName, *param, (bool)isCoDatatype));
+  env->ReleaseStringUTFChars(jName, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkDatatypeDecl
+ * Signature: (JLjava/lang/String;[JZ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkDatatypeDecl__JLjava_lang_String_2_3JZ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jName,
+    jlongArray jParams,
+    jboolean isCoDatatype)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  std::vector<Sort> params = getObjectsFromPointers<Sort>(env, jParams);
+  DatatypeDecl* retPointer = new DatatypeDecl(
+      solver->mkDatatypeDecl(cName, params, (bool)isCoDatatype));
+  env->ReleaseStringUTFChars(jName, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    simplify
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_simplify(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* retPointer = new Term(solver->simplify(*term));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    assertFormula
+ * Signature: (JJ)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_assertFormula(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  solver->assertFormula(*term);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    checkSat
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_checkSat(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Result* retPointer = new Result(solver->checkSat());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    checkSatAssuming
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_checkSatAssuming__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong assumptionPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* assumption = reinterpret_cast<Term*>(assumptionPointer);
+  Result* retPointer = new Result(solver->checkSatAssuming(*assumption));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    checkSatAssuming
+ * Signature: (J[J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_checkSatAssuming__J_3J(
+    JNIEnv* env, jobject, jlong pointer, jlongArray jAssumptions)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> assumptions =
+      getObjectsFromPointers<Term>(env, jAssumptions);
+  Result* retPointer = new Result(solver->checkSatAssuming(assumptions));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    checkEntailed
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_checkEntailed__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Result* retPointer = new Result(solver->checkEntailed(*term));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    checkEntailed
+ * Signature: (J[J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_checkEntailed__J_3J(
+    JNIEnv* env, jobject, jlong pointer, jlongArray jTerms)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
+  Result* retPointer = new Result(solver->checkEntailed(terms));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    declareDatatype
+ * Signature: (JLjava/lang/String;[J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_declareDatatype(
+    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jlongArray jCtors)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<DatatypeConstructorDecl> ctors =
+      getObjectsFromPointers<DatatypeConstructorDecl>(env, jCtors);
+  Sort* retPointer = new Sort(solver->declareDatatype(cSymbol, ctors));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    declareFun
+ * Signature: (JLjava/lang/String;[JJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_declareFun(JNIEnv* env,
+                                          jobject,
+                                          jlong pointer,
+                                          jstring jSymbol,
+                                          jlongArray jSorts,
+                                          jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, jSorts);
+  Term* retPointer = new Term(solver->declareFun(cSymbol, sorts, *sort));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    declareSort
+ * Signature: (JLjava/lang/String;I)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_declareSort(
+    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jint arity)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  Sort* retPointer = new Sort(solver->declareSort(cSymbol, (uint32_t)arity));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    defineFun
+ * Signature: (JLjava/lang/String;[JJJZ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_defineFun__JLjava_lang_String_2_3JJJZ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jSymbol,
+    jlongArray jVars,
+    jlong sortPointer,
+    jlong termPointer,
+    jboolean global)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer =
+      new Term(solver->defineFun(cSymbol, vars, *sort, *term, (bool)global));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    defineFun
+ * Signature: (JJ[JJZ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_defineFun__JJ_3JJZ(JNIEnv* env,
+                                                  jobject,
+                                                  jlong pointer,
+                                                  jlong funPointer,
+                                                  jlongArray jVars,
+                                                  jlong termPointer,
+                                                  jboolean global)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* fun = reinterpret_cast<Term*>(funPointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer =
+      new Term(solver->defineFun(*fun, vars, *term, (bool)global));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    defineFunRec
+ * Signature: (JLjava/lang/String;[JJJZ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_defineFunRec__JLjava_lang_String_2_3JJJZ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jSymbol,
+    jlongArray jVars,
+    jlong sortPointer,
+    jlong termPointer,
+    jboolean global)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer =
+      new Term(solver->defineFunRec(cSymbol, vars, *sort, *term, (bool)global));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    defineFunRec
+ * Signature: (JJ[JJZ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_defineFunRec__JJ_3JJZ(JNIEnv* env,
+                                                     jobject,
+                                                     jlong pointer,
+                                                     jlong funPointer,
+                                                     jlongArray jVars,
+                                                     jlong termPointer,
+                                                     jboolean global)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* fun = reinterpret_cast<Term*>(funPointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer =
+      new Term(solver->defineFunRec(*fun, vars, *term, (bool)global));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    defineFunsRec
+ * Signature: (J[J[[J[JZ)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Solver_defineFunsRec(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jlongArray jFuns,
+                                             jobjectArray jVars,
+                                             jlongArray jTerms,
+                                             jboolean global)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> funs = getObjectsFromPointers<Term>(env, jFuns);
+  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
+  std::vector<std::vector<Term>> varsMatrix;
+  jsize rows = env->GetArrayLength(jVars);
+  for (jint i = 0; i < rows; i++)
+  {
+    std::vector<Term> vars;
+    jlongArray row = (jlongArray)env->GetObjectArrayElement(jVars, i);
+    jsize columns = env->GetArrayLength(row);
+    jlong* columnElements = env->GetLongArrayElements(row, nullptr);
+    for (jint j = 0; j < columns; j++)
+    {
+      Term* var = reinterpret_cast<Term*>((jlongArray)columnElements[j]);
+      vars.push_back(*var);
+    }
+    varsMatrix.push_back(vars);
+  }
+  solver->defineFunsRec(funs, varsMatrix, terms, (bool)global);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getAssertions
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL Java_io_github_cvc5_api_Solver_getAssertions(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> assertions = solver->getAssertions();
+  jlongArray ret = getPointersFromObjects<Term>(env, assertions);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getInfo
+ * Signature: (JLjava/lang/String;)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Solver_getInfo(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer,
+                                                                 jstring jFlag)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jFlag, nullptr);
+  std::string cFlag(s);
+  env->ReleaseStringUTFChars(jFlag, s);
+  return env->NewStringUTF(solver->getInfo(cFlag).c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getOption
+ * Signature: (JLjava/lang/String;)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Solver_getOption(
+    JNIEnv* env, jobject, jlong pointer, jstring jOption)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jOption, nullptr);
+  std::string cOption(s);
+  env->ReleaseStringUTFChars(jOption, s);
+  return env->NewStringUTF(solver->getOption(cOption).c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getOptionNames
+ * Signature: (J)[Ljava/lang/String;
+ */
+JNIEXPORT jobjectArray JNICALL Java_io_github_cvc5_api_Solver_getOptionNames(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<std::string> options = solver->getOptionNames();
+  jobjectArray ret = getStringArrayFromStringVector(env, options);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getOptionInfo
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getOptionInfo(
+    JNIEnv* env, jobject, jlong pointer, jstring jOption)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::string cOption(env->GetStringUTFChars(jOption, nullptr));
+  OptionInfo* ret = new OptionInfo(solver->getOptionInfo(cOption));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getDriverOptions
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getDriverOptions(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  DriverOptions* ret = new DriverOptions(solver->getDriverOptions());
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getUnsatAssumptions
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL Java_io_github_cvc5_api_Solver_getUnsatAssumptions(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> core = solver->getUnsatAssumptions();
+  jlongArray ret = getPointersFromObjects<Term>(env, core);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getUnsatCore
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Solver_getUnsatCore(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> core = solver->getUnsatCore();
+  jlongArray ret = getPointersFromObjects<Term>(env, core);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getDifficulty
+ * Signature: (J)Ljava/util/Map;
+ */
+JNIEXPORT jobject JNICALL Java_io_github_cvc5_api_Solver_getDifficulty(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::map<Term, Term> map = solver->getDifficulty();
+  // HashMap hashMap = new HashMap();
+  jclass hashMapClass = env->FindClass("Ljava/util/HashMap;");
+  jmethodID constructor = env->GetMethodID(hashMapClass, "<init>", "()V");
+  jobject hashMap = env->NewObject(hashMapClass, constructor);
+  jmethodID putMethod = env->GetMethodID(
+      hashMapClass,
+      "put",
+      "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;");
+
+  // Long longObject = new Long(statPointer)
+  jclass longClass = env->FindClass("Ljava/lang/Long;");
+  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
+
+  for (const auto& [k, v] : map)
+  {
+    // hashmap.put(key, value);
+    Term* termKey = new Term(k);
+    Term* termValue = new Term(v);
+    jobject key = env->NewObject(
+        longClass, longConstructor, reinterpret_cast<jlong>(termKey));
+    jobject value = env->NewObject(
+        longClass, longConstructor, reinterpret_cast<jlong>(termValue));
+    env->CallObjectMethod(hashMap, putMethod, key, value);
+  }
+  return hashMap;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getProof
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Solver_getProof(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::string proof = solver->getProof();
+  return env->NewStringUTF(proof.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getValue
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getValue__JJ(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* retPointer = new Term(solver->getValue(*term));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getValue
+ * Signature: (J[J)[J
+ */
+JNIEXPORT jlongArray JNICALL Java_io_github_cvc5_api_Solver_getValue__J_3J(
+    JNIEnv* env, jobject, jlong pointer, jlongArray termPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> terms = getObjectsFromPointers<Term>(env, termPointers);
+  std::vector<Term> values = solver->getValue(terms);
+  jlongArray ret = getPointersFromObjects<Term>(env, values);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getModelDomainElements
+ * Signature: (JJ)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Solver_getModelDomainElements(JNIEnv* env,
+                                                      jobject,
+                                                      jlong pointer,
+                                                      jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  std::vector<Term> terms = solver->getModelDomainElements(*sort);
+  jlongArray ret = getPointersFromObjects<Term>(env, terms);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    isModelCoreSymbol
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Solver_isModelCoreSymbol(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  return static_cast<jboolean>(solver->isModelCoreSymbol(*term));
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getModel
+ * Signature: (J[J[J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Solver_getModel(JNIEnv* env,
+                                        jobject,
+                                        jlong pointer,
+                                        jlongArray sortPointers,
+                                        jlongArray varPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Sort> sorts = getObjectsFromPointers<Sort>(env, sortPointers);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, varPointers);
+  std::string model = solver->getModel(sorts, vars);
+  return env->NewStringUTF(model.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getQuantifierElimination
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getQuantifierElimination(
+    JNIEnv* env, jobject, jlong pointer, jlong qPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* q = reinterpret_cast<Term*>(qPointer);
+  Term* retPointer = new Term(solver->getQuantifierElimination(*q));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getQuantifierEliminationDisjunct
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_getQuantifierEliminationDisjunct(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer,
+                                                                jlong qPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* q = reinterpret_cast<Term*>(qPointer);
+  Term* retPointer = new Term(solver->getQuantifierEliminationDisjunct(*q));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    declareSeparationHeap
+ * Signature: (JJJ)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Solver_declareSeparationHeap(JNIEnv* env,
+                                                     jobject,
+                                                     jlong pointer,
+                                                     jlong locSortPointer,
+                                                     jlong dataSortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* locSort = reinterpret_cast<Sort*>(locSortPointer);
+  Sort* dataSort = reinterpret_cast<Sort*>(dataSortPointer);
+  solver->declareSeparationHeap(*locSort, *dataSort);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getSeparationHeap
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getSeparationHeap(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->getSeparationHeap());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getSeparationNilTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getSeparationNilTerm(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* retPointer = new Term(solver->getSeparationNilTerm());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    pop
+ * Signature: (JI)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_pop(JNIEnv* env,
+                                                          jobject,
+                                                          jlong pointer,
+                                                          jint nscopes)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  solver->pop((uint32_t)nscopes);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getInterpolant
+ * Signature: (JJJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Solver_getInterpolant__JJJ(
+    JNIEnv* env, jobject, jlong pointer, jlong conjPointer, jlong outputPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* conj = reinterpret_cast<Term*>(conjPointer);
+  Term* output = reinterpret_cast<Term*>(outputPointer);
+  return (jboolean)solver->getInterpolant(*conj, *output);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getInterpolant
+ * Signature: (JJJJ)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Solver_getInterpolant__JJJJ(JNIEnv* env,
+                                                    jobject,
+                                                    jlong pointer,
+                                                    jlong conjPointer,
+                                                    jlong grammarPointer,
+                                                    jlong outputPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* conj = reinterpret_cast<Term*>(conjPointer);
+  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
+  Term* output = reinterpret_cast<Term*>(outputPointer);
+  return (jboolean)solver->getInterpolant(*conj, *grammar, *output);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getAbduct
+ * Signature: (JJJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Solver_getAbduct__JJJ(
+    JNIEnv* env, jobject, jlong pointer, jlong conjPointer, jlong outputPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* conj = reinterpret_cast<Term*>(conjPointer);
+  Term* output = reinterpret_cast<Term*>(outputPointer);
+  return (jboolean)solver->getAbduct(*conj, *output);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getAbduct
+ * Signature: (JJJJ)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Solver_getAbduct__JJJJ(JNIEnv* env,
+                                               jobject,
+                                               jlong pointer,
+                                               jlong conjPointer,
+                                               jlong grammarPointer,
+                                               jlong outputPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* conj = reinterpret_cast<Term*>(conjPointer);
+  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
+  Term* output = reinterpret_cast<Term*>(outputPointer);
+  return (jboolean)solver->getAbduct(*conj, *grammar, *output);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    blockModel
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_blockModel(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  solver->blockModel();
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    blockModelValues
+ * Signature: (J[J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_blockModelValues(
+    JNIEnv* env, jobject, jlong pointer, jlongArray jTerms)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
+  solver->blockModelValues(terms);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    push
+ * Signature: (JI)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_push(JNIEnv* env,
+                                                           jobject,
+                                                           jlong pointer,
+                                                           jint nscopes)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  solver->push((uint32_t)nscopes);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    resetAssertions
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_resetAssertions(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  solver->resetAssertions();
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    setInfo
+ * Signature: (JLjava/lang/String;Ljava/lang/String;)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_setInfo(
+    JNIEnv* env, jobject, jlong pointer, jstring jKeyword, jstring jValue)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* sKeyword = env->GetStringUTFChars(jKeyword, nullptr);
+  const char* sValue = env->GetStringUTFChars(jValue, nullptr);
+  std::string cKeyword(sKeyword);
+  std::string cValue(sValue);
+  solver->setInfo(cKeyword, cValue);
+  env->ReleaseStringUTFChars(jKeyword, sKeyword);
+  env->ReleaseStringUTFChars(jValue, sValue);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    setLogic
+ * Signature: (JLjava/lang/String;)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_setLogic(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer,
+                                                               jstring jLogic)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* cLogic = env->GetStringUTFChars(jLogic, nullptr);
+  solver->setLogic(std::string(cLogic));
+
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    setOption
+ * Signature: (JLjava/lang/String;Ljava/lang/String;)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_setOption(
+    JNIEnv* env, jobject, jlong pointer, jstring jOption, jstring jValue)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* sOption = env->GetStringUTFChars(jOption, nullptr);
+  const char* sValue = env->GetStringUTFChars(jValue, nullptr);
+  std::string cOption(sOption);
+  std::string cValue(sValue);
+  solver->setOption(cOption, cValue);
+  env->ReleaseStringUTFChars(jOption, sOption);
+  env->ReleaseStringUTFChars(jValue, sValue);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    ensureTermSort
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_ensureTermSort(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Term* retPointer = new Term(solver->ensureTermSort(*term, *sort));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSygusVar
+ * Signature: (JJLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_mkSygusVar(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer, jstring jSymbol)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  Term* retPointer = new Term(solver->mkSygusVar(*sort, cSymbol));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    mkSygusGrammar
+ * Signature: (J[J[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_mkSygusGrammar(JNIEnv* env,
+                                              jobject,
+                                              jlong pointer,
+                                              jlongArray jBoundVars,
+                                              jlongArray jNtSymbols)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> boundVars = getObjectsFromPointers<Term>(env, jBoundVars);
+  std::vector<Term> ntSymbols = getObjectsFromPointers<Term>(env, jNtSymbols);
+  Grammar* retPointer =
+      new Grammar(solver->mkSygusGrammar(boundVars, ntSymbols));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    synthFun
+ * Signature: (JLjava/lang/String;[JJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_synthFun__JLjava_lang_String_2_3JJ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jSymbol,
+    jlongArray jVars,
+    jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Term> boundVars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer = new Term(solver->synthFun(cSymbol, boundVars, *sort));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    synthFun
+ * Signature: (JLjava/lang/String;[JJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_synthFun__JLjava_lang_String_2_3JJJ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jSymbol,
+    jlongArray jVars,
+    jlong sortPointer,
+    jlong grammarPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Term> boundVars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer =
+      new Term(solver->synthFun(cSymbol, boundVars, *sort, *grammar));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    synthInv
+ * Signature: (JLjava/lang/String;[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_synthInv__JLjava_lang_String_2_3J(
+    JNIEnv* env, jobject, jlong pointer, jstring jSymbol, jlongArray jVars)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer = new Term(solver->synthInv(cSymbol, vars));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    synthInv
+ * Signature: (JLjava/lang/String;[JJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_synthInv__JLjava_lang_String_2_3JJ(
+    JNIEnv* env,
+    jobject,
+    jlong pointer,
+    jstring jSymbol,
+    jlongArray jVars,
+    jlong grammarPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Grammar* grammar = reinterpret_cast<Grammar*>(grammarPointer);
+  const char* s = env->GetStringUTFChars(jSymbol, nullptr);
+  std::string cSymbol(s);
+  std::vector<Term> vars = getObjectsFromPointers<Term>(env, jVars);
+  Term* retPointer = new Term(solver->synthInv(cSymbol, vars, *grammar));
+  env->ReleaseStringUTFChars(jSymbol, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    addSygusConstraint
+ * Signature: (JJ)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_addSygusConstraint(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  solver->addSygusConstraint(*term);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    addSygusAssume
+ * Signature: (JJ)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Solver_addSygusAssume(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  solver->addSygusAssume(*term);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    addSygusInvConstraint
+ * Signature: (JJJJJ)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Solver_addSygusInvConstraint(JNIEnv* env,
+                                                     jobject,
+                                                     jlong pointer,
+                                                     jlong invPointer,
+                                                     jlong prePointer,
+                                                     jlong transPointer,
+                                                     jlong postPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* inv = reinterpret_cast<Term*>(invPointer);
+  Term* pre = reinterpret_cast<Term*>(prePointer);
+  Term* trans = reinterpret_cast<Term*>(transPointer);
+  Term* post = reinterpret_cast<Term*>(postPointer);
+  solver->addSygusInvConstraint(*inv, *pre, *trans, *post);
+  CVC5_JAVA_API_TRY_CATCH_END(env);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    checkSynth
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_checkSynth(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Result* retPointer = new Result(solver->checkSynth());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getSynthSolution
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getSynthSolution(
+    JNIEnv* env, jobject, jlong pointer, jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* retPointer = new Term(solver->getSynthSolution(*term));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getSynthSolutions
+ * Signature: (J[J)[J
+ */
+JNIEXPORT jlongArray JNICALL Java_io_github_cvc5_api_Solver_getSynthSolutions(
+    JNIEnv* env, jobject, jlong pointer, jlongArray jTerms)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  std::vector<Term> terms = getObjectsFromPointers<Term>(env, jTerms);
+  std::vector<Term> solutions = solver->getSynthSolutions(terms);
+  jlongArray ret = getPointersFromObjects<Term>(env, solutions);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getStatistics
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getStatistics(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Solver* solver = reinterpret_cast<Solver*>(pointer);
+  Statistics* retPointer = new Statistics(solver->getStatistics());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getNullTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getNullTerm(JNIEnv* env,
+                                                                   jobject,
+                                                                   jlong)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* ret = new Term();
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getNullResult
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_getNullResult(JNIEnv* env, jobject, jlong)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Result* ret = new Result();
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getNullOp
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Solver_getNullOp(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Op* ret = new Op();
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Solver
+ * Method:    getNullDatatypeDecl
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Solver_getNullDatatypeDecl(JNIEnv* env, jobject, jlong)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  DatatypeDecl* ret = new DatatypeDecl();
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
\ No newline at end of file
diff --git a/src/api/java/jni/sort.cpp b/src/api/java/jni/sort.cpp
new file mode 100644 (file)
index 0000000..fed1f3a
--- /dev/null
@@ -0,0 +1,1067 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Sort.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Sort_deletePointer(JNIEnv*,
+                                                                  jclass,
+                                                                  jlong pointer)
+{
+  delete reinterpret_cast<Sort*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    equals
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_equals(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer1,
+                                                               jlong pointer2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort sort1 = *(reinterpret_cast<Sort*>(pointer1));
+  Sort sort2 = *(reinterpret_cast<Sort*>(pointer2));
+  return static_cast<jboolean>((sort1 == sort2));
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    compareTo
+ * Signature: (JJ)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Sort_compareTo(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer1,
+                                                              jlong pointer2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* sort1 = reinterpret_cast<Sort*>(pointer1);
+  Sort* sort2 = reinterpret_cast<Sort*>(pointer2);
+  if (*sort1 < *sort2)
+  {
+    return static_cast<jint>(-1);
+  }
+  if (*sort1 == *sort2)
+  {
+    return 0;
+  }
+  return static_cast<jint>(1);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isNull(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isNull());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isBoolean
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isBoolean(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isBoolean());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isInteger
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isInteger(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isInteger());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isReal
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isReal(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isReal());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isString
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isString(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isString());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isRegExp
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isRegExp(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isRegExp());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isRoundingMode
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isRoundingMode(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isRoundingMode());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isBitVector
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isBitVector(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isBitVector());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isFloatingPoint
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isFloatingPoint(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPoint());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isDatatype
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isDatatype(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isDatatype());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isParametricDatatype
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isParametricDatatype(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isParametricDatatype());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isConstructor
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isConstructor(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isConstructor());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isSelector
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isSelector(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isSelector());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isTester
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isTester(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isTester());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isUpdater
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isUpdater(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isUpdater());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isFunction
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isFunction(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isFunction());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isPredicate
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isPredicate(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isPredicate());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isTuple
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isTuple(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isTuple());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isRecord
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isRecord(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isRecord());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isArray
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isArray(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isArray());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isSet
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isSet(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isSet());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isBag
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isBag(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isBag());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isSequence
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isSequence(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isSequence());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isUninterpretedSort
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isUninterpretedSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isUninterpretedSort());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isSortConstructor
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isSortConstructor(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isSortConstructor());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isFirstClass
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isFirstClass(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isFirstClass());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isFunctionLike
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isFunctionLike(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isFunctionLike());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isSubsortOf
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isSubsortOf(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  return static_cast<jboolean>(current->isSubsortOf(*sort));
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isComparableTo
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Sort_isComparableTo(
+    JNIEnv* env, jobject, jlong pointer, jlong sortPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  return static_cast<jboolean>(current->isComparableTo(*sort));
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getDatatype
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getDatatype(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Datatype* retPointer = new Datatype(current->getDatatype());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    instantiate
+ * Signature: (J[J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_instantiate(
+    JNIEnv* env, jobject, jlong pointer, jlongArray paramsPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  // get the size of params pointers
+  jsize size = env->GetArrayLength(paramsPointers);
+  // allocate buffer for the long array
+  jlong* buffer = new jlong[size];
+  // copy java array to the buffer
+  env->GetLongArrayRegion(paramsPointers, 0, size, buffer);
+  // copy the terms into a vector
+  std::vector<Sort> params;
+  for (jsize i = 0; i < size; i++)
+  {
+    Sort* sort = reinterpret_cast<Sort*>(buffer[i]);
+    params.push_back(*sort);
+  }
+  // free the buffer memory
+  delete[] buffer;
+
+  Sort* retPointer = new Sort(current->instantiate(params));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    substitute
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Sort_substitute__JJJ(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jlong sortPointer,
+                                             jlong replacementPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* sort = reinterpret_cast<Sort*>(sortPointer);
+  Sort* replacement = reinterpret_cast<Sort*>(replacementPointer);
+  Sort* retPointer = new Sort(current->substitute(*sort, *replacement));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    substitute
+ * Signature: (J[J[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Sort_substitute__J_3J_3J(JNIEnv* env,
+                                                 jobject,
+                                                 jlong pointer,
+                                                 jlongArray sortPointers,
+                                                 jlongArray replacementPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  // get the size of pointers
+  jsize sortsSize = env->GetArrayLength(sortPointers);
+  jsize replacementsSize = env->GetArrayLength(replacementPointers);
+  // allocate buffer for the long array
+  jlong* sortsBuffer = new jlong[sortsSize];
+  jlong* replacementsBuffer = new jlong[replacementsSize];
+  // copy java array to the buffer
+  env->GetLongArrayRegion(sortPointers, 0, sortsSize, sortsBuffer);
+  env->GetLongArrayRegion(
+      replacementPointers, 0, replacementsSize, replacementsBuffer);
+  // copy the terms into a vector
+  std::vector<Sort> sorts;
+  for (jsize i = 0; i < sortsSize; i++)
+  {
+    Sort* sort = reinterpret_cast<Sort*>(sortsBuffer[i]);
+    sorts.push_back(*sort);
+  }
+
+  std::vector<Sort> replacements;
+  for (jsize i = 0; i < replacementsSize; i++)
+  {
+    Sort* sort = reinterpret_cast<Sort*>(replacementsBuffer[i]);
+    replacements.push_back(*sort);
+  }
+
+  // free the buffer memory
+  delete[] sortsBuffer;
+  delete[] replacementsBuffer;
+
+  Sort* retPointer = new Sort(current->substitute(sorts, replacements));
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Sort_toString(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getConstructorArity
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Sort_getConstructorArity(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getConstructorArity());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getConstructorDomainSorts
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Sort_getConstructorDomainSorts(JNIEnv* env,
+                                                       jobject,
+                                                       jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  std::vector<Sort> sorts = current->getConstructorDomainSorts();
+  std::vector<long> sortPointers(sorts.size());
+  for (size_t i = 0; i < sorts.size(); i++)
+  {
+    sortPointers[i] = (long)new Sort(sorts[i]);
+  }
+  jlongArray ret = env->NewLongArray(sorts.size());
+  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getConstructorCodomainSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getConstructorCodomainSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getConstructorCodomainSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getSelectorDomainSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getSelectorDomainSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getSelectorDomainSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getSelectorCodomainSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getSelectorCodomainSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getSelectorCodomainSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getTesterDomainSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getTesterDomainSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getTesterDomainSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getTesterCodomainSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getTesterCodomainSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getTesterCodomainSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getFunctionArity
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Sort_getFunctionArity(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getFunctionArity());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getFunctionDomainSorts
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Sort_getFunctionDomainSorts(JNIEnv* env,
+                                                    jobject,
+                                                    jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  std::vector<Sort> sorts = current->getFunctionDomainSorts();
+  std::vector<long> sortPointers(sorts.size());
+  for (size_t i = 0; i < sorts.size(); i++)
+  {
+    sortPointers[i] = (long)new Sort(sorts[i]);
+  }
+  jlongArray ret = env->NewLongArray(sorts.size());
+  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getFunctionCodomainSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getFunctionCodomainSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getFunctionCodomainSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getArrayIndexSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getArrayIndexSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getArrayIndexSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getArrayElementSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getArrayElementSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getArrayElementSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getSetElementSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getSetElementSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getSetElementSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getBagElementSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getBagElementSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getBagElementSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getSequenceElementSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Sort_getSequenceElementSort(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  Sort* retPointer = new Sort(current->getSequenceElementSort());
+  return (jlong)retPointer;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getUninterpretedSortName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Sort_getUninterpretedSortName(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return env->NewStringUTF(current->getUninterpretedSortName().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    isUninterpretedSortParameterized
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Sort_isUninterpretedSortParameterized(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jboolean>(current->isUninterpretedSortParameterized());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getUninterpretedSortParamSorts
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Sort_getUninterpretedSortParamSorts(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  std::vector<Sort> sorts = current->getUninterpretedSortParamSorts();
+  std::vector<long> sortPointers(sorts.size());
+  for (size_t i = 0; i < sorts.size(); i++)
+  {
+    sortPointers[i] = (long)new Sort(sorts[i]);
+  }
+  jlongArray ret = env->NewLongArray(sorts.size());
+  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getSortConstructorName
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Sort_getSortConstructorName(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return env->NewStringUTF(current->getSortConstructorName().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getSortConstructorArity
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Sort_getSortConstructorArity(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getSortConstructorArity());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getBitVectorSize
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Sort_getBitVectorSize(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getBitVectorSize());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getFloatingPointExponentSize
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL
+Java_io_github_cvc5_api_Sort_getFloatingPointExponentSize(JNIEnv* env,
+                                                          jobject,
+                                                          jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getFloatingPointExponentSize());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getFloatingPointSignificandSize
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL
+Java_io_github_cvc5_api_Sort_getFloatingPointSignificandSize(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getFloatingPointSignificandSize());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getDatatypeParamSorts
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL Java_io_github_cvc5_api_Sort_getDatatypeParamSorts(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  std::vector<Sort> sorts = current->getDatatypeParamSorts();
+  std::vector<long> sortPointers(sorts.size());
+  for (size_t i = 0; i < sorts.size(); i++)
+  {
+    sortPointers[i] = (long)new Sort(sorts[i]);
+  }
+  jlongArray ret = env->NewLongArray(sorts.size());
+  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getDatatypeArity
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Sort_getDatatypeArity(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getDatatypeArity());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getTupleLength
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL
+Java_io_github_cvc5_api_Sort_getTupleLength(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  return static_cast<jint>(current->getTupleLength());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Sort
+ * Method:    getTupleSorts
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Sort_getTupleSorts(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Sort* current = reinterpret_cast<Sort*>(pointer);
+  std::vector<Sort> sorts = current->getTupleSorts();
+  std::vector<long> sortPointers(sorts.size());
+  for (size_t i = 0; i < sorts.size(); i++)
+  {
+    sortPointers[i] = (long)new Sort(sorts[i]);
+  }
+  jlongArray ret = env->NewLongArray(sorts.size());
+  env->SetLongArrayRegion(ret, 0, sorts.size(), sortPointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/stat.cpp b/src/api/java/jni/stat.cpp
new file mode 100644 (file)
index 0000000..5db362c
--- /dev/null
@@ -0,0 +1,220 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Stat.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Stat_deletePointer(JNIEnv*,
+                                                                  jclass,
+                                                                  jlong pointer)
+{
+  delete reinterpret_cast<Stat*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Stat_toString(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  std::stringstream ss;
+  ss << *current;
+  return env->NewStringUTF(ss.str().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    isExpert
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Stat_isExpert(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jboolean>(current->isExpert());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    isDefault
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Stat_isDefault(JNIEnv* env,
+                                                                  jobject,
+                                                                  jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jboolean>(current->isDefault());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    isInt
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Stat_isInt(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jboolean>(current->isInt());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    getInt
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Stat_getInt(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jlong>(current->getInt());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jlong>(0));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    isDouble
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Stat_isDouble(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jboolean>(current->isDouble());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    getDouble
+ * Signature: (J)D
+ */
+JNIEXPORT jdouble JNICALL Java_io_github_cvc5_api_Stat_getDouble(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jdouble>(current->getDouble());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jdouble>(0));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    isString
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Stat_isString(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jboolean>(current->isString());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    getString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Stat_getString(JNIEnv* env,
+                                                                 jobject,
+                                                                 jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return env->NewStringUTF(current->getString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    isHistogram
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Stat_isHistogram(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  return static_cast<jboolean>(current->isHistogram());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Stat
+ * Method:    getHistogram
+ * Signature: (J)Ljava/util/Map;
+ */
+JNIEXPORT jobject JNICALL
+Java_io_github_cvc5_api_Stat_getHistogram(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Stat* current = reinterpret_cast<Stat*>(pointer);
+  std::map<std::string, uint64_t> histogram = current->getHistogram();
+  // HashMap hashMap = new HashMap();
+  jclass hashMapClass = env->FindClass("Ljava/util/HashMap;");
+  jmethodID constructor = env->GetMethodID(hashMapClass, "<init>", "()V");
+  jobject hashMap = env->NewObject(hashMapClass, constructor);
+  jmethodID putMethod = env->GetMethodID(
+      hashMapClass,
+      "put",
+      "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;");
+
+  // Long longObject = new Long(statPointer)
+  jclass longClass = env->FindClass("Ljava/lang/Long;");
+  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
+
+  for (const std::pair<const std::basic_string<char>, uint64_t>& it : histogram)
+  {
+    // hashmap.put(key, value);
+    jstring key = env->NewStringUTF(it.first.c_str());
+    jobject value = env->NewObject(
+        longClass, longConstructor, static_cast<jlong>(it.second));
+    env->CallObjectMethod(hashMap, putMethod, key, value);
+  }
+  return hashMap;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
diff --git a/src/api/java/jni/statistics.cpp b/src/api/java/jni/statistics.cpp
new file mode 100644 (file)
index 0000000..827c318
--- /dev/null
@@ -0,0 +1,171 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include <sstream>
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Statistics.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL
+Java_io_github_cvc5_api_Statistics_deletePointer(JNIEnv*, jclass, jlong pointer)
+{
+  delete reinterpret_cast<Statistics*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Statistics_toString(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+
+  Statistics* current = reinterpret_cast<Statistics*>(pointer);
+  std::stringstream ss;
+  ss << *current;
+  return env->NewStringUTF(ss.str().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    get
+ * Signature: (JLjava/lang/String;)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Statistics_get(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer,
+                                                               jstring jName)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Statistics* current = reinterpret_cast<Statistics*>(pointer);
+  const char* s = env->GetStringUTFChars(jName, nullptr);
+  std::string cName(s);
+  Stat* retPointer = new Stat(current->get(cName));
+  env->ReleaseStringUTFChars(jName, s);
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    getIterator
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Statistics_getIterator(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Statistics* current = reinterpret_cast<Statistics*>(pointer);
+  Statistics::iterator* it =
+      new Statistics::iterator(current->begin(true, true));
+  return reinterpret_cast<jlong>(it);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    hasNext
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Statistics_hasNext(
+    JNIEnv* env, jobject, jlong pointer, jlong iteratorPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Statistics* current = reinterpret_cast<Statistics*>(pointer);
+  Statistics::iterator it =
+      *reinterpret_cast<Statistics::iterator*>(iteratorPointer);
+  return static_cast<jboolean>(it != current->end());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    getNext
+ * Signature: (JJ)Lio/github/cvc5/api/Pair;
+ */
+JNIEXPORT jobject JNICALL Java_io_github_cvc5_api_Statistics_getNext(
+    JNIEnv* env, jobject, jlong, jlong iteratorPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Statistics::iterator it =
+      *reinterpret_cast<Statistics::iterator*>(iteratorPointer);
+  std::string cName = it->first;
+  jstring jName = env->NewStringUTF(cName.c_str());
+  Stat* stat = new Stat(it->second);
+  jlong statPointer = reinterpret_cast<jlong>(stat);
+
+  // Long longObject = new Long(statPointer)
+  jclass longClass = env->FindClass("Ljava/lang/Long;");
+  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
+  jobject longObject = env->NewObject(longClass, longConstructor, statPointer);
+
+  // Pair<String, Long> pair = new Pair<String, Long>(jName, longObject)
+  jclass pairClass = env->FindClass("Lio/github/cvc5/api/Pair;");
+  jmethodID pairConstructor = env->GetMethodID(
+      pairClass, "<init>", "(Ljava/lang/Object;Ljava/lang/Object;)V");
+  jobject pair = env->NewObject(pairClass, pairConstructor, jName, longObject);
+
+  it++;
+  return pair;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    increment
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Statistics_increment(
+    JNIEnv* env, jobject, jlong pointer, jlong iteratorPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Statistics* current = reinterpret_cast<Statistics*>(pointer);
+  Statistics::iterator* itPointer =
+      reinterpret_cast<Statistics::iterator*>(iteratorPointer);
+  Statistics::iterator it = *itPointer;
+  if (it == current->end())
+  {
+    delete itPointer;
+    std::string message = "Reached the end of Statistics::iterator";
+    throw CVC5ApiException(message);
+  }
+
+  Statistics::iterator* nextIt = new Statistics::iterator(it.operator++());
+  delete itPointer;
+  return reinterpret_cast<jlong>(nextIt);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Statistics
+ * Method:    deleteIteratorPointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Statistics_deleteIteratorPointer(
+    JNIEnv*, jobject, jlong iteratorPointer)
+{
+  delete reinterpret_cast<Statistics::iterator*>(iteratorPointer);
+}
diff --git a/src/api/java/jni/term.cpp b/src/api/java/jni/term.cpp
new file mode 100644 (file)
index 0000000..5c8300e
--- /dev/null
@@ -0,0 +1,895 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * The cvc5 Java API.
+ */
+
+#include "api/cpp/cvc5.h"
+#include "api_utilities.h"
+#include "io_github_cvc5_api_Term.h"
+
+using namespace cvc5::api;
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    deletePointer
+ * Signature: (J)V
+ */
+JNIEXPORT void JNICALL Java_io_github_cvc5_api_Term_deletePointer(JNIEnv* env,
+                                                                  jclass,
+                                                                  jlong pointer)
+{
+  delete reinterpret_cast<Term*>(pointer);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    equals
+ * Signature: (JJ)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_equals(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer1,
+                                                               jlong pointer2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* term1 = reinterpret_cast<Term*>(pointer1);
+  Term* term2 = reinterpret_cast<Term*>(pointer2);
+  // We compare the actual terms, not their pointers.
+  return static_cast<jboolean>(*term1 == *term2);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    compareTo
+ * Signature: (JJ)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Term_compareTo(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer1,
+                                                              jlong pointer2)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* term1 = reinterpret_cast<Term*>(pointer1);
+  Term* term2 = reinterpret_cast<Term*>(pointer2);
+  if (*term1 < *term2)
+  {
+    return static_cast<jint>(-1);
+  }
+  if (*term1 == *term2)
+  {
+    return 0;
+  }
+  return static_cast<jint>(1);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getNumChildren
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL
+Java_io_github_cvc5_api_Term_getNumChildren(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jint>(current->getNumChildren());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getChild
+ * Signature: (JI)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_getChild(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer,
+                                                              jint index)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* ret = new Term((*current)[static_cast<size_t>(index)]);
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getId
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_getId(JNIEnv* env,
+                                                           jobject,
+                                                           jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jlong>(current->getId());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getKind
+ * Signature: (J)I
+ */
+JNIEXPORT jint JNICALL Java_io_github_cvc5_api_Term_getKind(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jint>(current->getKind());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getSort
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_getSort(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Sort* ret = new Sort(current->getSort());
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    substitute
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Term_substitute__JJJ(JNIEnv* env,
+                                             jobject,
+                                             jlong pointer,
+                                             jlong termPointer,
+                                             jlong replacementPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* replacement = reinterpret_cast<Term*>(replacementPointer);
+  Term* ret = new Term(current->substitute(*term, *replacement));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    substitute
+ * Signature: (J[J[J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_io_github_cvc5_api_Term_substitute__J_3J_3J(JNIEnv* env,
+                                                 jobject,
+                                                 jlong pointer,
+                                                 jlongArray termPointers,
+                                                 jlongArray replacementPointers)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  jsize termsSize = env->GetArrayLength(termPointers);
+  jsize replacementsSize = env->GetArrayLength(replacementPointers);
+  jlong* termElements = env->GetLongArrayElements(termPointers, nullptr);
+  jlong* replacementElements =
+      env->GetLongArrayElements(replacementPointers, nullptr);
+
+  std::vector<Term> terms(termsSize);
+  std::vector<Term> replacements(replacementsSize);
+
+  for (jsize i = 0; i < termsSize; i++)
+  {
+    Term* term = (Term*)termElements[i];
+    terms[i] = *term;
+  }
+  env->ReleaseLongArrayElements(termPointers, termElements, 0);
+
+  for (jsize i = 0; i < replacementsSize; i++)
+  {
+    Term* term = (Term*)replacementElements[i];
+    replacements[i] = *term;
+  }
+  env->ReleaseLongArrayElements(replacementPointers, replacementElements, 0);
+
+  Term* ret = new Term(current->substitute(terms, replacements));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    hasOp
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_hasOp(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->hasOp());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getOp
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_getOp(JNIEnv* env,
+                                                           jobject,
+                                                           jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Op* ret = new Op(current->getOp());
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isNull
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isNull(JNIEnv* env,
+                                                               jobject,
+                                                               jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isNull());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isConstArray
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isConstArray(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isConstArray());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getConstArrayBase
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_getConstArrayBase(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* ret = new Term(current->getConstArrayBase());
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    notTerm
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_notTerm(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* ret = new Term(current->notTerm());
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    andTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_andTerm(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer,
+                                                             jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* ret = new Term(current->andTerm(*term));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    orTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_orTerm(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer,
+                                                            jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* ret = new Term(current->orTerm(*term));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    xorTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_xorTerm(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer,
+                                                             jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* ret = new Term(current->xorTerm(*term));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    eqTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_eqTerm(JNIEnv* env,
+                                                            jobject,
+                                                            jlong pointer,
+                                                            jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* ret = new Term(current->eqTerm(*term));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    impTerm
+ * Signature: (JJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_impTerm(JNIEnv* env,
+                                                             jobject,
+                                                             jlong pointer,
+                                                             jlong termPointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* term = reinterpret_cast<Term*>(termPointer);
+  Term* ret = new Term(current->impTerm(*term));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    iteTerm
+ * Signature: (JJJ)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_iteTerm(
+    JNIEnv* env, jobject, jlong pointer, jlong thenPointer, jlong elsePointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term* thenTerm = reinterpret_cast<Term*>(thenPointer);
+  Term* elseTerm = reinterpret_cast<Term*>(elsePointer);
+  Term* ret = new Term(current->iteTerm(*thenTerm, *elseTerm));
+  return reinterpret_cast<jlong>(ret);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    toString
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Term_toString(JNIEnv* env,
+                                                                jobject,
+                                                                jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return env->NewStringUTF(current->toString().c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isIntegerValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isIntegerValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isIntegerValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getIntegerValue
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Term_getIntegerValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::string value = current->getIntegerValue();
+  jstring ret = env->NewStringUTF(value.c_str());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isStringValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isStringValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isStringValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getStringValue
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Term_getStringValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::wstring termString = current->getStringValue();
+
+  size_t length = termString.length();
+  jchar* unicode = new jchar[length];
+  const wchar_t* s = termString.c_str();
+  for (size_t i = 0; i < length; i++)
+  {
+    unicode[i] = s[i];
+  }
+  jstring ret = env->NewString(unicode, length);
+  delete[] unicode;
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isRealValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isRealValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isRealValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getRealValue
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL
+Java_io_github_cvc5_api_Term_getRealValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::string realValue = current->getRealValue();
+  return env->NewStringUTF(realValue.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isBooleanValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isBooleanValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isBooleanValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getBooleanValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_getBooleanValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->getBooleanValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isBitVectorValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isBitVectorValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isBitVectorValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getBitVectorValue
+ * Signature: (JI)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Term_getBitVectorValue(
+    JNIEnv* env, jobject, jlong pointer, jint base)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::string ret =
+      current->getBitVectorValue(static_cast<std::uint32_t>(base));
+  return env->NewStringUTF(ret.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isAbstractValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isAbstractValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isAbstractValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getAbstractValue
+ * Signature: (J)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_io_github_cvc5_api_Term_getAbstractValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::string ret = current->getAbstractValue();
+  return env->NewStringUTF(ret.c_str());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isTupleValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isTupleValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isTupleValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getTupleValue
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Term_getTupleValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::vector<Term> terms = current->getTupleValue();
+  jlongArray ret = getPointersFromObjects<Term>(env, terms);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isFloatingPointPosZero
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isFloatingPointPosZero(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPointPosZero());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isFloatingPointNegZero
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isFloatingPointNegZero(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPointNegZero());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isFloatingPointPosInf
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isFloatingPointPosInf(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPointPosInf());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isFloatingPointNegInf
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isFloatingPointNegInf(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPointNegInf());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isFloatingPointNaN
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isFloatingPointNaN(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPointNaN());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isFloatingPointValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isFloatingPointValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isFloatingPointValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getFloatingPointValue
+ * Signature: (J)Lio/github/cvc5/api/Triplet;
+ */
+JNIEXPORT jobject JNICALL Java_io_github_cvc5_api_Term_getFloatingPointValue(
+    JNIEnv* env, jobject thisObject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  auto [exponent, significand, term] = current->getFloatingPointValue();
+  Term* termPointer = new Term(term);
+
+  // Long longObject = new Long(pointer)
+  jclass longClass = env->FindClass("Ljava/lang/Long;");
+  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
+  jobject e = env->NewObject(longClass, longConstructor, exponent);
+  jobject s = env->NewObject(longClass, longConstructor, significand);
+  jobject t = env->NewObject(longClass, longConstructor, termPointer);
+
+  // Triplet triplet = new Triplet<Long, Long, Long>(e, s, t);
+  jclass tripletClass = env->FindClass("Lio/github/cvc5/api/Triplet;");
+  jmethodID tripletConstructor = env->GetMethodID(
+      tripletClass,
+      "<init>",
+      "(Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)V");
+  jobject triplet = env->NewObject(tripletClass, tripletConstructor, e, s, t);
+
+  return triplet;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isSetValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL
+Java_io_github_cvc5_api_Term_isSetValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isSetValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getSetValue
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL
+Java_io_github_cvc5_api_Term_getSetValue(JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::set<Term> terms = current->getSetValue();
+  std::vector<jlong> pointers(terms.size());
+  int i = 0;
+  for (const Term& t : terms)
+  {
+    pointers[i] = reinterpret_cast<jlong>(new Term(t));
+    i++;
+  }
+  jlongArray ret = env->NewLongArray(pointers.size());
+  env->SetLongArrayRegion(ret, 0, pointers.size(), pointers.data());
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isSequenceValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isSequenceValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isSequenceValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getSequenceValue
+ * Signature: (J)[J
+ */
+JNIEXPORT jlongArray JNICALL Java_io_github_cvc5_api_Term_getSequenceValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::vector<Term> terms = current->getSequenceValue();
+  jlongArray ret = getPointersFromObjects<Term>(env, terms);
+  return ret;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    isUninterpretedValue
+ * Signature: (J)Z
+ */
+JNIEXPORT jboolean JNICALL Java_io_github_cvc5_api_Term_isUninterpretedValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  return static_cast<jboolean>(current->isUninterpretedValue());
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, static_cast<jboolean>(false));
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    getUninterpretedValue
+ * Signature: (J)Lio/github/cvc5/api/Pair;
+ */
+JNIEXPORT jobject JNICALL Java_io_github_cvc5_api_Term_getUninterpretedValue(
+    JNIEnv* env, jobject, jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  std::pair<Sort, std::int32_t> value = current->getUninterpretedValue();
+
+  Sort* sort = new Sort(value.first);
+  jlong sortPointer = reinterpret_cast<jlong>(sort);
+
+  // Long longObject = new Long(pointer)
+  jclass longClass = env->FindClass("Ljava/lang/Long;");
+  jmethodID longConstructor = env->GetMethodID(longClass, "<init>", "(J)V");
+  jobject longObject = env->NewObject(longClass, longConstructor, sortPointer);
+
+  // Integer integerObject = new Integer(pair.second)
+  jclass integerClass = env->FindClass("Ljava/lang/Integer;");
+  jmethodID integerConstructor =
+      env->GetMethodID(integerClass, "<init>", "(I)V");
+  jobject integerObject = env->NewObject(
+      integerClass, integerConstructor, static_cast<jint>(value.second));
+
+  // Pair<String, Long> pair = new Pair<String, Long>(jName, longObject)
+  jclass pairClass = env->FindClass("Lio/github/cvc5/api/Pair;");
+  jmethodID pairConstructor = env->GetMethodID(
+      pairClass, "<init>", "(Ljava/lang/Object;Ljava/lang/Object;)V");
+  jobject pair =
+      env->NewObject(pairClass, pairConstructor, longObject, integerObject);
+
+  return pair;
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, nullptr);
+}
+
+/*
+ * Class:     io_github_cvc5_api_Term
+ * Method:    iterator
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL Java_io_github_cvc5_api_Term_iterator(JNIEnv* env,
+                                                              jobject,
+                                                              jlong pointer)
+{
+  CVC5_JAVA_API_TRY_CATCH_BEGIN;
+  Term* current = reinterpret_cast<Term*>(pointer);
+  Term::const_iterator* retPointer = new Term::const_iterator(current->begin());
+  return reinterpret_cast<jlong>(retPointer);
+  CVC5_JAVA_API_TRY_CATCH_END_RETURN(env, 0);
+}
index 66b764ca4944c940ecc905463026234b567ef928..61ae74fd28a0b77140ce614c65ab3299a2353287 100644 (file)
@@ -21,13 +21,13 @@ get_target_property(CVC5_JAR_PATH cvc5jar JAR_FILE)
 
 # specify source files for junit tests
 set(java_test_src_files
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/DatatypeTest.java
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/GrammarTest.java
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/OpTest.java
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/ResultTest.java
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/SolverTest.java
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/SortTest.java
-  ${CMAKE_CURRENT_SOURCE_DIR}/cvc5/TermTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/DatatypeTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/GrammarTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/OpTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/ResultTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/SolverTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/SortTest.java
+  ${CMAKE_CURRENT_SOURCE_DIR}/TermTest.java
 )
 
 # build junit tests
@@ -59,7 +59,7 @@ add_custom_target(
     -Djava.library.path=${CVC5_JNI_PATH}
     -jar ${JUnit_JAR}
     -cp ${JUnit_JAR}:${CVC5_JAR_PATH}:.
-    -select-package cvc5
+    -select-package tests
   COMMENT "Run junit tests"
   VERBATIM
 )
diff --git a/test/unit/api/java/DatatypeTest.java b/test/unit/api/java/DatatypeTest.java
new file mode 100644 (file)
index 0000000..cd9d7ee
--- /dev/null
@@ -0,0 +1,566 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Andrew Reynolds, Aina Niemetz, Andres Noetzli, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the datatype classes of the Java API.
+ */
+
+package tests;
+import static io.github.cvc5.api.Kind.*;
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import java.util.*;
+import java.util.concurrent.atomic.AtomicReference;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+class DatatypeTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  @Test void mkDatatypeSort() throws CVC5ApiException
+  {
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    Sort listSort = d_solver.mkDatatypeSort(dtypeSpec);
+    Datatype d = listSort.getDatatype();
+    DatatypeConstructor consConstr = d.getConstructor(0);
+    DatatypeConstructor nilConstr = d.getConstructor(1);
+    assertThrows(CVC5ApiException.class, () -> d.getConstructor(2));
+    assertDoesNotThrow(() -> consConstr.getConstructorTerm());
+    assertDoesNotThrow(() -> nilConstr.getConstructorTerm());
+  }
+
+  @Test void mkDatatypeSorts()
+  {
+    /* Create two mutual datatypes corresponding to this definition
+     * block:
+     *
+     *   DATATYPE
+     *     tree = node(left: tree, right: tree) | leaf(data: list),
+     *     list = cons(car: tree, cdr: list) | nil
+     *   END;
+     */
+    // Make unresolved types as placeholders
+    Set<Sort> unresTypes = new HashSet<>();
+    Sort unresTree = d_solver.mkUninterpretedSort("tree");
+    Sort unresList = d_solver.mkUninterpretedSort("list");
+    unresTypes.add(unresTree);
+    unresTypes.add(unresList);
+
+    DatatypeDecl tree = d_solver.mkDatatypeDecl("tree");
+    DatatypeConstructorDecl node = d_solver.mkDatatypeConstructorDecl("node");
+    node.addSelector("left", unresTree);
+    node.addSelector("right", unresTree);
+    tree.addConstructor(node);
+
+    DatatypeConstructorDecl leaf = d_solver.mkDatatypeConstructorDecl("leaf");
+    leaf.addSelector("data", unresList);
+    tree.addConstructor(leaf);
+
+    DatatypeDecl list = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("car", unresTree);
+    cons.addSelector("cdr", unresTree);
+    list.addConstructor(cons);
+
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    list.addConstructor(nil);
+
+    List<DatatypeDecl> dtdecls = new ArrayList<>();
+    dtdecls.add(tree);
+    dtdecls.add(list);
+
+    AtomicReference<List<Sort>> atomic = new AtomicReference<>();
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    List<Sort> dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), dtdecls.size());
+    for (int i = 0, ndecl = dtdecls.size(); i < ndecl; i++)
+    {
+      assertTrue(dtsorts.get(i).isDatatype());
+      assertFalse(dtsorts.get(i).getDatatype().isFinite());
+      assertEquals(dtsorts.get(i).getDatatype().getName(), dtdecls.get(i).getName());
+    }
+    // verify the resolution was correct
+    Datatype dtTree = dtsorts.get(0).getDatatype();
+    DatatypeConstructor dtcTreeNode = dtTree.getConstructor(0);
+    assertEquals(dtcTreeNode.getName(), "node");
+    DatatypeSelector dtsTreeNodeLeft = dtcTreeNode.getSelector(0);
+    assertEquals(dtsTreeNodeLeft.getName(), "left");
+    // argument type should have resolved to be recursive
+    assertTrue(dtsTreeNodeLeft.getRangeSort().isDatatype());
+    assertEquals(dtsTreeNodeLeft.getRangeSort(), dtsorts.get(0));
+
+    // fails due to empty datatype
+    List<DatatypeDecl> dtdeclsBad = new ArrayList<>();
+    DatatypeDecl emptyD = d_solver.mkDatatypeDecl("emptyD");
+    dtdeclsBad.add(emptyD);
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkDatatypeSorts(dtdeclsBad));
+  }
+
+  @Test void datatypeStructs() throws CVC5ApiException
+  {
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+
+    // create datatype sort to test
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", intSort);
+    cons.addSelectorSelf("tail");
+    Sort nullSort = d_solver.getNullSort();
+    assertThrows(CVC5ApiException.class, () -> cons.addSelector("null", nullSort));
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
+    Datatype dt = dtypeSort.getDatatype();
+    assertFalse(dt.isCodatatype());
+    assertFalse(dt.isTuple());
+    assertFalse(dt.isRecord());
+    assertFalse(dt.isFinite());
+    assertTrue(dt.isWellFounded());
+    // get constructor
+    DatatypeConstructor dcons = dt.getConstructor(0);
+    Term consTerm = dcons.getConstructorTerm();
+    assertEquals(dcons.getNumSelectors(), 2);
+
+    // create datatype sort to test
+    DatatypeDecl dtypeSpecEnum = d_solver.mkDatatypeDecl("enum");
+    DatatypeConstructorDecl ca = d_solver.mkDatatypeConstructorDecl("A");
+    dtypeSpecEnum.addConstructor(ca);
+    DatatypeConstructorDecl cb = d_solver.mkDatatypeConstructorDecl("B");
+    dtypeSpecEnum.addConstructor(cb);
+    DatatypeConstructorDecl cc = d_solver.mkDatatypeConstructorDecl("C");
+    dtypeSpecEnum.addConstructor(cc);
+    Sort dtypeSortEnum = d_solver.mkDatatypeSort(dtypeSpecEnum);
+    Datatype dtEnum = dtypeSortEnum.getDatatype();
+    assertFalse(dtEnum.isTuple());
+    assertTrue(dtEnum.isFinite());
+
+    // create codatatype
+    DatatypeDecl dtypeSpecStream = d_solver.mkDatatypeDecl("stream", true);
+    DatatypeConstructorDecl consStream = d_solver.mkDatatypeConstructorDecl("cons");
+    consStream.addSelector("head", intSort);
+    consStream.addSelectorSelf("tail");
+    dtypeSpecStream.addConstructor(consStream);
+    Sort dtypeSortStream = d_solver.mkDatatypeSort(dtypeSpecStream);
+    Datatype dtStream = dtypeSortStream.getDatatype();
+    assertTrue(dtStream.isCodatatype());
+    assertFalse(dtStream.isFinite());
+    // codatatypes may be well-founded
+    assertTrue(dtStream.isWellFounded());
+
+    // create tuple
+    Sort tupSort = d_solver.mkTupleSort(new Sort[] {boolSort});
+    Datatype dtTuple = tupSort.getDatatype();
+    assertTrue(dtTuple.isTuple());
+    assertFalse(dtTuple.isRecord());
+    assertTrue(dtTuple.isFinite());
+    assertTrue(dtTuple.isWellFounded());
+
+    // create record
+    Pair<String, Sort>[] fields = new Pair[] {new Pair<>("b", boolSort), new Pair<>("i", intSort)};
+    Sort recSort = d_solver.mkRecordSort(fields);
+    assertTrue(recSort.isDatatype());
+    Datatype dtRecord = recSort.getDatatype();
+    assertFalse(dtRecord.isTuple());
+    assertTrue(dtRecord.isRecord());
+    assertFalse(dtRecord.isFinite());
+    assertTrue(dtRecord.isWellFounded());
+  }
+
+  @Test void datatypeNames() throws CVC5ApiException
+  {
+    Sort intSort = d_solver.getIntegerSort();
+
+    // create datatype sort to test
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    assertDoesNotThrow(() -> dtypeSpec.getName());
+    assertEquals(dtypeSpec.getName(), "list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", intSort);
+    cons.addSelectorSelf("tail");
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
+    Datatype dt = dtypeSort.getDatatype();
+    assertEquals(dt.getName(), "list");
+    assertDoesNotThrow(() -> dt.getConstructor("nil"));
+    assertDoesNotThrow(() -> dt.getConstructor("cons"));
+    assertThrows(CVC5ApiException.class, () -> dt.getConstructor("head"));
+    assertThrows(CVC5ApiException.class, () -> dt.getConstructor(""));
+
+    DatatypeConstructor dcons = dt.getConstructor(0);
+    assertEquals(dcons.getName(), "cons");
+    assertDoesNotThrow(() -> dcons.getSelector("head"));
+    assertDoesNotThrow(() -> dcons.getSelector("tail"));
+    assertThrows(CVC5ApiException.class, () -> dcons.getSelector("cons"));
+
+    // get selector
+    DatatypeSelector dselTail = dcons.getSelector(1);
+    assertEquals(dselTail.getName(), "tail");
+    assertEquals(dselTail.getRangeSort(), dtypeSort);
+
+    // possible to construct null datatype declarations if not using solver
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullDatatypeDecl().getName());
+  }
+
+  @Test void parametricDatatype() throws CVC5ApiException
+  {
+    List<Sort> v = new ArrayList<>();
+    Sort t1 = d_solver.mkParamSort("T1");
+    Sort t2 = d_solver.mkParamSort("T2");
+    v.add(t1);
+    v.add(t2);
+    DatatypeDecl pairSpec = d_solver.mkDatatypeDecl("pair", v);
+
+    DatatypeConstructorDecl mkpair = d_solver.mkDatatypeConstructorDecl("mk-pair");
+    mkpair.addSelector("first", t1);
+    mkpair.addSelector("second", t2);
+    pairSpec.addConstructor(mkpair);
+
+    Sort pairType = d_solver.mkDatatypeSort(pairSpec);
+
+    assertTrue(pairType.getDatatype().isParametric());
+
+    v.clear();
+    v.add(d_solver.getIntegerSort());
+    v.add(d_solver.getIntegerSort());
+    Sort pairIntInt = pairType.instantiate(v);
+    v.clear();
+    v.add(d_solver.getRealSort());
+    v.add(d_solver.getRealSort());
+    Sort pairRealReal = pairType.instantiate(v);
+    v.clear();
+    v.add(d_solver.getRealSort());
+    v.add(d_solver.getIntegerSort());
+    Sort pairRealInt = pairType.instantiate(v);
+    v.clear();
+    v.add(d_solver.getIntegerSort());
+    v.add(d_solver.getRealSort());
+    Sort pairIntReal = pairType.instantiate(v);
+
+    assertNotEquals(pairIntInt, pairRealReal);
+    assertNotEquals(pairIntReal, pairRealReal);
+    assertNotEquals(pairRealInt, pairRealReal);
+    assertNotEquals(pairIntInt, pairIntReal);
+    assertNotEquals(pairIntInt, pairRealInt);
+    assertNotEquals(pairIntReal, pairRealInt);
+
+    assertTrue(pairRealReal.isComparableTo(pairRealReal));
+    assertFalse(pairIntReal.isComparableTo(pairRealReal));
+    assertFalse(pairRealInt.isComparableTo(pairRealReal));
+    assertFalse(pairIntInt.isComparableTo(pairRealReal));
+    assertFalse(pairRealReal.isComparableTo(pairRealInt));
+    assertFalse(pairIntReal.isComparableTo(pairRealInt));
+    assertTrue(pairRealInt.isComparableTo(pairRealInt));
+    assertFalse(pairIntInt.isComparableTo(pairRealInt));
+    assertFalse(pairRealReal.isComparableTo(pairIntReal));
+    assertTrue(pairIntReal.isComparableTo(pairIntReal));
+    assertFalse(pairRealInt.isComparableTo(pairIntReal));
+    assertFalse(pairIntInt.isComparableTo(pairIntReal));
+    assertFalse(pairRealReal.isComparableTo(pairIntInt));
+    assertFalse(pairIntReal.isComparableTo(pairIntInt));
+    assertFalse(pairRealInt.isComparableTo(pairIntInt));
+    assertTrue(pairIntInt.isComparableTo(pairIntInt));
+
+    assertTrue(pairRealReal.isSubsortOf(pairRealReal));
+    assertFalse(pairIntReal.isSubsortOf(pairRealReal));
+    assertFalse(pairRealInt.isSubsortOf(pairRealReal));
+    assertFalse(pairIntInt.isSubsortOf(pairRealReal));
+    assertFalse(pairRealReal.isSubsortOf(pairRealInt));
+    assertFalse(pairIntReal.isSubsortOf(pairRealInt));
+    assertTrue(pairRealInt.isSubsortOf(pairRealInt));
+    assertFalse(pairIntInt.isSubsortOf(pairRealInt));
+    assertFalse(pairRealReal.isSubsortOf(pairIntReal));
+    assertTrue(pairIntReal.isSubsortOf(pairIntReal));
+    assertFalse(pairRealInt.isSubsortOf(pairIntReal));
+    assertFalse(pairIntInt.isSubsortOf(pairIntReal));
+    assertFalse(pairRealReal.isSubsortOf(pairIntInt));
+    assertFalse(pairIntReal.isSubsortOf(pairIntInt));
+    assertFalse(pairRealInt.isSubsortOf(pairIntInt));
+    assertTrue(pairIntInt.isSubsortOf(pairIntInt));
+  }
+
+  @Test void datatypeSimplyRec() throws CVC5ApiException
+  {
+    /* Create mutual datatypes corresponding to this definition block:
+     *
+     *   DATATYPE
+     *     wlist = leaf(data: list),
+     *     list = cons(car: wlist, cdr: list) | nil,
+     *     ns = elem(ndata: set(wlist)) | elemArray(ndata2: array(list, list))
+     *   END;
+     */
+    // Make unresolved types as placeholders
+    Set<Sort> unresTypes = new HashSet<>();
+    Sort unresWList = d_solver.mkUninterpretedSort("wlist");
+    Sort unresList = d_solver.mkUninterpretedSort("list");
+    Sort unresNs = d_solver.mkUninterpretedSort("ns");
+    unresTypes.add(unresWList);
+    unresTypes.add(unresList);
+    unresTypes.add(unresNs);
+
+    DatatypeDecl wlist = d_solver.mkDatatypeDecl("wlist");
+    DatatypeConstructorDecl leaf = d_solver.mkDatatypeConstructorDecl("leaf");
+    leaf.addSelector("data", unresList);
+    wlist.addConstructor(leaf);
+
+    DatatypeDecl list = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("car", unresWList);
+    cons.addSelector("cdr", unresList);
+    list.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    list.addConstructor(nil);
+
+    DatatypeDecl ns = d_solver.mkDatatypeDecl("ns");
+    DatatypeConstructorDecl elem = d_solver.mkDatatypeConstructorDecl("elem");
+    elem.addSelector("ndata", d_solver.mkSetSort(unresWList));
+    ns.addConstructor(elem);
+    DatatypeConstructorDecl elemArray = d_solver.mkDatatypeConstructorDecl("elemArray");
+    elemArray.addSelector("ndata", d_solver.mkArraySort(unresList, unresList));
+    ns.addConstructor(elemArray);
+
+    List<DatatypeDecl> dtdecls = new ArrayList<>();
+    dtdecls.add(wlist);
+    dtdecls.add(list);
+    dtdecls.add(ns);
+    // this is well-founded and has no nested recursion
+    AtomicReference<List<Sort>> atomic = new AtomicReference<>();
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    List<Sort> dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), 3);
+    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(1).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(2).getDatatype().isWellFounded());
+    assertFalse(dtsorts.get(0).getDatatype().hasNestedRecursion());
+    assertFalse(dtsorts.get(1).getDatatype().hasNestedRecursion());
+    assertFalse(dtsorts.get(2).getDatatype().hasNestedRecursion());
+
+    /* Create mutual datatypes corresponding to this definition block:
+     *   DATATYPE
+     *     ns2 = elem2(ndata: array(int,ns2)) | nil2
+     *   END;
+     */
+    unresTypes.clear();
+    Sort unresNs2 = d_solver.mkUninterpretedSort("ns2");
+    unresTypes.add(unresNs2);
+
+    DatatypeDecl ns2 = d_solver.mkDatatypeDecl("ns2");
+    DatatypeConstructorDecl elem2 = d_solver.mkDatatypeConstructorDecl("elem2");
+    elem2.addSelector("ndata", d_solver.mkArraySort(d_solver.getIntegerSort(), unresNs2));
+    ns2.addConstructor(elem2);
+    DatatypeConstructorDecl nil2 = d_solver.mkDatatypeConstructorDecl("nil2");
+    ns2.addConstructor(nil2);
+
+    dtdecls.clear();
+    dtdecls.add(ns2);
+
+    // dtsorts.clear();
+    // this is not well-founded due to non-simple recursion
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), 1);
+    assertTrue(
+        dtsorts.get(0).getDatatype().getConstructor(0).getSelector(0).getRangeSort().isArray());
+    assertEquals(dtsorts.get(0)
+                     .getDatatype()
+                     .getConstructor(0)
+                     .getSelector(0)
+                     .getRangeSort()
+                     .getArrayElementSort(),
+        dtsorts.get(0));
+    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
+
+    /* Create mutual datatypes corresponding to this definition block:
+     *   DATATYPE
+     *     list3 = cons3(car: ns3, cdr: list3) | nil3,
+     *     ns3 = elem3(ndata: set(list3))
+     *   END;
+     */
+    unresTypes.clear();
+    Sort unresNs3 = d_solver.mkUninterpretedSort("ns3");
+    unresTypes.add(unresNs3);
+    Sort unresList3 = d_solver.mkUninterpretedSort("list3");
+    unresTypes.add(unresList3);
+
+    DatatypeDecl list3 = d_solver.mkDatatypeDecl("list3");
+    DatatypeConstructorDecl cons3 = d_solver.mkDatatypeConstructorDecl("cons3");
+    cons3.addSelector("car", unresNs3);
+    cons3.addSelector("cdr", unresList3);
+    list3.addConstructor(cons3);
+    DatatypeConstructorDecl nil3 = d_solver.mkDatatypeConstructorDecl("nil3");
+    list3.addConstructor(nil3);
+
+    DatatypeDecl ns3 = d_solver.mkDatatypeDecl("ns3");
+    DatatypeConstructorDecl elem3 = d_solver.mkDatatypeConstructorDecl("elem3");
+    elem3.addSelector("ndata", d_solver.mkSetSort(unresList3));
+    ns3.addConstructor(elem3);
+
+    dtdecls.clear();
+    dtdecls.add(list3);
+    dtdecls.add(ns3);
+
+    // dtsorts.clear();
+    // both are well-founded and have nested recursion
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), 2);
+    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(1).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
+    assertTrue(dtsorts.get(1).getDatatype().hasNestedRecursion());
+
+    /* Create mutual datatypes corresponding to this definition block:
+     *   DATATYPE
+     *     list4 = cons(car: set(ns4), cdr: list4) | nil,
+     *     ns4 = elem(ndata: list4)
+     *   END;
+     */
+    unresTypes.clear();
+    Sort unresNs4 = d_solver.mkUninterpretedSort("ns4");
+    unresTypes.add(unresNs4);
+    Sort unresList4 = d_solver.mkUninterpretedSort("list4");
+    unresTypes.add(unresList4);
+
+    DatatypeDecl list4 = d_solver.mkDatatypeDecl("list4");
+    DatatypeConstructorDecl cons4 = d_solver.mkDatatypeConstructorDecl("cons4");
+    cons4.addSelector("car", d_solver.mkSetSort(unresNs4));
+    cons4.addSelector("cdr", unresList4);
+    list4.addConstructor(cons4);
+    DatatypeConstructorDecl nil4 = d_solver.mkDatatypeConstructorDecl("nil4");
+    list4.addConstructor(nil4);
+
+    DatatypeDecl ns4 = d_solver.mkDatatypeDecl("ns4");
+    DatatypeConstructorDecl elem4 = d_solver.mkDatatypeConstructorDecl("elem3");
+    elem4.addSelector("ndata", unresList4);
+    ns4.addConstructor(elem4);
+
+    dtdecls.clear();
+    dtdecls.add(list4);
+    dtdecls.add(ns4);
+
+    // dtsorts.clear();
+    // both are well-founded and have nested recursion
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), 2);
+    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(1).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
+    assertTrue(dtsorts.get(1).getDatatype().hasNestedRecursion());
+
+    /* Create mutual datatypes corresponding to this definition block:
+     *   DATATYPE
+     *     list5[X] = cons(car: X, cdr: list5[list5[X]]) | nil
+     *   END;
+     */
+    unresTypes.clear();
+    Sort unresList5 = d_solver.mkSortConstructorSort("list5", 1);
+    unresTypes.add(unresList5);
+
+    List<Sort> v = new ArrayList<>();
+    Sort x = d_solver.mkParamSort("X");
+    v.add(x);
+    DatatypeDecl list5 = d_solver.mkDatatypeDecl("list5", v);
+
+    List<Sort> args = new ArrayList<>();
+    args.add(x);
+    Sort urListX = unresList5.instantiate(args);
+    args.set(0, urListX);
+    Sort urListListX = unresList5.instantiate(args);
+
+    DatatypeConstructorDecl cons5 = d_solver.mkDatatypeConstructorDecl("cons5");
+    cons5.addSelector("car", x);
+    cons5.addSelector("cdr", urListListX);
+    list5.addConstructor(cons5);
+    DatatypeConstructorDecl nil5 = d_solver.mkDatatypeConstructorDecl("nil5");
+    list5.addConstructor(nil5);
+
+    dtdecls.clear();
+    dtdecls.add(list5);
+
+    // well-founded and has nested recursion
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), 1);
+    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
+    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
+  }
+
+  @Test void datatypeSpecializedCons() throws CVC5ApiException
+  {
+    /* Create mutual datatypes corresponding to this definition block:
+     *   DATATYPE
+     *     plist[X] = pcons(car: X, cdr: plist[X]) | pnil
+     *   END;
+     */
+    // Make unresolved types as placeholders
+    Set<Sort> unresTypes = new HashSet<>();
+    Sort unresList = d_solver.mkSortConstructorSort("plist", 1);
+    unresTypes.add(unresList);
+
+    List<Sort> v = new ArrayList<>();
+    Sort x = d_solver.mkParamSort("X");
+    v.add(x);
+    DatatypeDecl plist = d_solver.mkDatatypeDecl("plist", v);
+
+    List<Sort> args = new ArrayList<>();
+    args.add(x);
+    Sort urListX = unresList.instantiate(args);
+
+    DatatypeConstructorDecl pcons = d_solver.mkDatatypeConstructorDecl("pcons");
+    pcons.addSelector("car", x);
+    pcons.addSelector("cdr", urListX);
+    plist.addConstructor(pcons);
+    DatatypeConstructorDecl nil5 = d_solver.mkDatatypeConstructorDecl("pnil");
+    plist.addConstructor(nil5);
+
+    List<DatatypeDecl> dtdecls = new ArrayList<>();
+    dtdecls.add(plist);
+
+    // make the datatype sorts
+    AtomicReference<List<Sort>> atomic = new AtomicReference<>();
+    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
+    List<Sort> dtsorts = atomic.get();
+    assertEquals(dtsorts.size(), 1);
+    Datatype d = dtsorts.get(0).getDatatype();
+    DatatypeConstructor nilc = d.getConstructor(0);
+
+    Sort isort = d_solver.getIntegerSort();
+    List<Sort> iargs = new ArrayList<>();
+    iargs.add(isort);
+    Sort listInt = dtsorts.get(0).instantiate(iargs);
+
+    AtomicReference<Term> atomicTerm = new AtomicReference<>();
+    // get the specialized constructor term for list[Int]
+    assertDoesNotThrow(() -> atomicTerm.set(nilc.getSpecializedConstructorTerm(listInt)));
+    Term testConsTerm = atomicTerm.get();
+    assertNotEquals(testConsTerm, nilc.getConstructorTerm());
+    // error to get the specialized constructor term for Int
+    assertThrows(CVC5ApiException.class, () -> nilc.getSpecializedConstructorTerm(isort));
+  }
+}
diff --git a/test/unit/api/java/GrammarTest.java b/test/unit/api/java/GrammarTest.java
new file mode 100644 (file)
index 0000000..e9b0d73
--- /dev/null
@@ -0,0 +1,131 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Abdalrhman Mohamed, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the guards of the Java API functions.
+ */
+
+package tests;
+import static io.github.cvc5.api.Kind.*;
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import java.util.Arrays;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+class GrammarTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  @Test void addRule()
+  {
+    Sort bool = d_solver.getBooleanSort();
+    Sort integer = d_solver.getIntegerSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term start = d_solver.mkVar(bool);
+    Term nts = d_solver.mkVar(bool);
+
+    Grammar g = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
+
+    assertDoesNotThrow(() -> g.addRule(start, d_solver.mkBoolean(false)));
+
+    assertThrows(CVC5ApiException.class, () -> g.addRule(nullTerm, d_solver.mkBoolean(false)));
+    assertThrows(CVC5ApiException.class, () -> g.addRule(start, nullTerm));
+    assertThrows(CVC5ApiException.class, () -> g.addRule(nts, d_solver.mkBoolean(false)));
+    assertThrows(CVC5ApiException.class, () -> g.addRule(start, d_solver.mkInteger(0)));
+    assertThrows(CVC5ApiException.class, () -> g.addRule(start, nts));
+
+    d_solver.synthFun("f", new Term[] {}, bool, g);
+
+    assertThrows(CVC5ApiException.class, () -> g.addRule(start, d_solver.mkBoolean(false)));
+  }
+
+  @Test void addRules()
+  {
+    Sort bool = d_solver.getBooleanSort();
+    Sort integer = d_solver.getIntegerSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term start = d_solver.mkVar(bool);
+    Term nts = d_solver.mkVar(bool);
+
+    Grammar g = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
+
+    assertDoesNotThrow(() -> g.addRules(start, new Term[] {d_solver.mkBoolean(false)}));
+
+    assertThrows(
+        CVC5ApiException.class, () -> g.addRules(nullTerm, new Term[] {d_solver.mkBoolean(false)}));
+    assertThrows(CVC5ApiException.class, () -> g.addRules(start, new Term[] {nullTerm}));
+    assertThrows(
+        CVC5ApiException.class, () -> g.addRules(nts, new Term[] {d_solver.mkBoolean(false)}));
+    assertThrows(
+        CVC5ApiException.class, () -> g.addRules(start, new Term[] {d_solver.mkInteger(0)}));
+    assertThrows(CVC5ApiException.class, () -> g.addRules(start, new Term[] {nts}));
+
+    d_solver.synthFun("f", new Term[] {}, bool, g);
+
+    assertThrows(
+        CVC5ApiException.class, () -> g.addRules(start, new Term[] {d_solver.mkBoolean(false)}));
+  }
+
+  @Test void addAnyConstant()
+  {
+    Sort bool = d_solver.getBooleanSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term start = d_solver.mkVar(bool);
+    Term nts = d_solver.mkVar(bool);
+
+    Grammar g = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
+
+    assertDoesNotThrow(() -> g.addAnyConstant(start));
+    assertDoesNotThrow(() -> g.addAnyConstant(start));
+
+    assertThrows(CVC5ApiException.class, () -> g.addAnyConstant(nullTerm));
+    assertThrows(CVC5ApiException.class, () -> g.addAnyConstant(nts));
+
+    d_solver.synthFun("f", new Term[] {}, bool, g);
+
+    assertThrows(CVC5ApiException.class, () -> g.addAnyConstant(start));
+  }
+
+  @Test void addAnyVariable()
+  {
+    Sort bool = d_solver.getBooleanSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term x = d_solver.mkVar(bool);
+    Term start = d_solver.mkVar(bool);
+    Term nts = d_solver.mkVar(bool);
+
+    Grammar g1 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start});
+    Grammar g2 = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
+
+    assertDoesNotThrow(() -> g1.addAnyVariable(start));
+    assertDoesNotThrow(() -> g1.addAnyVariable(start));
+    assertDoesNotThrow(() -> g2.addAnyVariable(start));
+
+    assertThrows(CVC5ApiException.class, () -> g1.addAnyVariable(nullTerm));
+    assertThrows(CVC5ApiException.class, () -> g1.addAnyVariable(nts));
+
+    d_solver.synthFun("f", new Term[] {}, bool, g1);
+
+    assertThrows(CVC5ApiException.class, () -> g1.addAnyVariable(start));
+  }
+}
diff --git a/test/unit/api/java/OpTest.java b/test/unit/api/java/OpTest.java
new file mode 100644 (file)
index 0000000..c631571
--- /dev/null
@@ -0,0 +1,157 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Makai Mann, Aina Niemetz, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the Op class.
+ */
+
+package tests;
+import static io.github.cvc5.api.Kind.*;
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import java.util.Arrays;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+class OpTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  @Test void getKind() throws CVC5ApiException
+  {
+    Op x;
+    x = d_solver.mkOp(BITVECTOR_EXTRACT, 31, 1);
+    assertDoesNotThrow(() -> x.getKind());
+  }
+
+  @Test void isNull() throws CVC5ApiException
+  {
+    Op x = d_solver.getNullOp();
+    assertTrue(x.isNull());
+    x = d_solver.mkOp(BITVECTOR_EXTRACT, 31, 1);
+    assertFalse(x.isNull());
+  }
+
+  @Test void opFromKind()
+  {
+    assertDoesNotThrow(() -> d_solver.mkOp(PLUS));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT));
+  }
+
+  @Test void getIndicesString() throws CVC5ApiException
+  {
+    Op x = d_solver.getNullOp();
+    assertThrows(CVC5ApiException.class, () -> x.getStringIndices());
+
+    Op divisible_ot = d_solver.mkOp(DIVISIBLE, 4);
+    assertTrue(divisible_ot.isIndexed());
+    String divisible_idx = divisible_ot.getStringIndices()[0];
+    assertEquals(divisible_idx, "4");
+  }
+
+  @Test void getIndicesUint() throws CVC5ApiException
+  {
+    Op bitvector_repeat_ot = d_solver.mkOp(BITVECTOR_REPEAT, 5);
+    assertTrue(bitvector_repeat_ot.isIndexed());
+    int bitvector_repeat_idx = bitvector_repeat_ot.getIntegerIndices()[0];
+    assertEquals(bitvector_repeat_idx, 5);
+
+    // unlike bitvector_repeat_ot.getIndices<std::pair<uint32_t, uint32_t>>() in
+    // c++, this does not throw in Java
+    // assertThrows(CVC5ApiException.class,
+    //              () -> bitvector_repeat_ot.getIntegerIndices());
+
+    Op bitvector_zero_extend_ot = d_solver.mkOp(BITVECTOR_ZERO_EXTEND, 6);
+    int bitvector_zero_extend_idx = bitvector_zero_extend_ot.getIntegerIndices()[0];
+    assertEquals(bitvector_zero_extend_idx, 6);
+
+    Op bitvector_sign_extend_ot = d_solver.mkOp(BITVECTOR_SIGN_EXTEND, 7);
+    int bitvector_sign_extend_idx = bitvector_sign_extend_ot.getIntegerIndices()[0];
+    assertEquals(bitvector_sign_extend_idx, 7);
+
+    Op bitvector_rotate_left_ot = d_solver.mkOp(BITVECTOR_ROTATE_LEFT, 8);
+    int bitvector_rotate_left_idx = bitvector_rotate_left_ot.getIntegerIndices()[0];
+    assertEquals(bitvector_rotate_left_idx, 8);
+
+    Op bitvector_rotate_right_ot = d_solver.mkOp(BITVECTOR_ROTATE_RIGHT, 9);
+    int bitvector_rotate_right_idx = bitvector_rotate_right_ot.getIntegerIndices()[0];
+    assertEquals(bitvector_rotate_right_idx, 9);
+
+    Op int_to_bitvector_ot = d_solver.mkOp(INT_TO_BITVECTOR, 10);
+    int int_to_bitvector_idx = int_to_bitvector_ot.getIntegerIndices()[0];
+    assertEquals(int_to_bitvector_idx, 10);
+
+    Op floatingpoint_to_ubv_ot = d_solver.mkOp(FLOATINGPOINT_TO_UBV, 11);
+    int floatingpoint_to_ubv_idx = floatingpoint_to_ubv_ot.getIntegerIndices()[0];
+    assertEquals(floatingpoint_to_ubv_idx, 11);
+
+    Op floatingpoint_to_sbv_ot = d_solver.mkOp(FLOATINGPOINT_TO_SBV, 13);
+    int floatingpoint_to_sbv_idx = floatingpoint_to_sbv_ot.getIntegerIndices()[0];
+    assertEquals(floatingpoint_to_sbv_idx, 13);
+  }
+
+  @Test void getIndicesPairUint() throws CVC5ApiException
+  {
+    Op bitvector_extract_ot = d_solver.mkOp(BITVECTOR_EXTRACT, 4, 0);
+    assertTrue(bitvector_extract_ot.isIndexed());
+    int[] bitvector_extract_indices = bitvector_extract_ot.getIntegerIndices();
+    assertArrayEquals(bitvector_extract_indices, new int[] {4, 0});
+
+    Op floatingpoint_to_fp_ieee_bitvector_ot =
+        d_solver.mkOp(FLOATINGPOINT_TO_FP_IEEE_BITVECTOR, 4, 25);
+    int[] floatingpoint_to_fp_ieee_bitvector_indices =
+        floatingpoint_to_fp_ieee_bitvector_ot.getIntegerIndices();
+    assertArrayEquals(floatingpoint_to_fp_ieee_bitvector_indices, new int[] {4, 25});
+
+    Op floatingpoint_to_fp_floatingpoint_ot =
+        d_solver.mkOp(FLOATINGPOINT_TO_FP_FLOATINGPOINT, 4, 25);
+    int[] floatingpoint_to_fp_floatingpoint_indices =
+        floatingpoint_to_fp_floatingpoint_ot.getIntegerIndices();
+    assertArrayEquals(floatingpoint_to_fp_floatingpoint_indices, new int[] {4, 25});
+
+    Op floatingpoint_to_fp_real_ot = d_solver.mkOp(FLOATINGPOINT_TO_FP_REAL, 4, 25);
+    int[] floatingpoint_to_fp_real_indices = floatingpoint_to_fp_real_ot.getIntegerIndices();
+    assertArrayEquals(floatingpoint_to_fp_real_indices, new int[] {4, 25});
+
+    Op floatingpoint_to_fp_signed_bitvector_ot =
+        d_solver.mkOp(FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR, 4, 25);
+    int[] floatingpoint_to_fp_signed_bitvector_indices =
+        floatingpoint_to_fp_signed_bitvector_ot.getIntegerIndices();
+    assertArrayEquals(floatingpoint_to_fp_signed_bitvector_indices, new int[] {4, 25});
+
+    Op floatingpoint_to_fp_unsigned_bitvector_ot =
+        d_solver.mkOp(FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR, 4, 25);
+    int[] floatingpoint_to_fp_unsigned_bitvector_indices =
+        floatingpoint_to_fp_unsigned_bitvector_ot.getIntegerIndices();
+    assertArrayEquals(floatingpoint_to_fp_unsigned_bitvector_indices, new int[] {4, 25});
+
+    Op floatingpoint_to_fp_generic_ot = d_solver.mkOp(FLOATINGPOINT_TO_FP_GENERIC, 4, 25);
+    int[] floatingpoint_to_fp_generic_indices = floatingpoint_to_fp_generic_ot.getIntegerIndices();
+    assertArrayEquals(floatingpoint_to_fp_generic_indices, new int[] {4, 25});
+    assertThrows(CVC5ApiException.class, () -> floatingpoint_to_fp_generic_ot.getStringIndices());
+  }
+
+  @Test void opScopingToString() throws CVC5ApiException
+  {
+    Op bitvector_repeat_ot = d_solver.mkOp(BITVECTOR_REPEAT, 5);
+    String op_repr = bitvector_repeat_ot.toString();
+
+    Solver solver2;
+    assertEquals(bitvector_repeat_ot.toString(), op_repr);
+  }
+}
diff --git a/test/unit/api/java/ResultTest.java b/test/unit/api/java/ResultTest.java
new file mode 100644 (file)
index 0000000..38e9818
--- /dev/null
@@ -0,0 +1,127 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the Result class
+ */
+
+package tests;
+
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+class ResultTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  @Test void isNull()
+  {
+    Result res_null = d_solver.getNullResult();
+    assertTrue(res_null.isNull());
+    assertFalse(res_null.isSat());
+    assertFalse(res_null.isUnsat());
+    assertFalse(res_null.isSatUnknown());
+    assertFalse(res_null.isEntailed());
+    assertFalse(res_null.isNotEntailed());
+    assertFalse(res_null.isEntailmentUnknown());
+    Sort u_sort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkVar(u_sort, "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    Result res = d_solver.checkSat();
+    assertFalse(res.isNull());
+  }
+
+  @Test void eq()
+  {
+    Sort u_sort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkVar(u_sort, "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    Result res;
+    Result res2 = d_solver.checkSat();
+    Result res3 = d_solver.checkSat();
+    res = res2;
+    assertEquals(res, res2);
+    assertEquals(res3, res2);
+  }
+
+  @Test void isSat()
+  {
+    Sort u_sort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkVar(u_sort, "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    Result res = d_solver.checkSat();
+    assertTrue(res.isSat());
+    assertFalse(res.isSatUnknown());
+  }
+
+  @Test void isUnsat()
+  {
+    Sort u_sort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkVar(u_sort, "x");
+    d_solver.assertFormula(x.eqTerm(x).notTerm());
+    Result res = d_solver.checkSat();
+    assertTrue(res.isUnsat());
+    assertFalse(res.isSatUnknown());
+  }
+
+  @Test void isSatUnknown() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_NIA");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("solve-int-as-bv", "32");
+    Sort int_sort = d_solver.getIntegerSort();
+    Term x = d_solver.mkVar(int_sort, "x");
+    d_solver.assertFormula(x.eqTerm(x).notTerm());
+    Result res = d_solver.checkSat();
+    assertFalse(res.isSat());
+    assertTrue(res.isSatUnknown());
+  }
+
+  @Test void isEntailed()
+  {
+    d_solver.setOption("incremental", "true");
+    Sort u_sort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkConst(u_sort, "x");
+    Term y = d_solver.mkConst(u_sort, "y");
+    Term a = x.eqTerm(y).notTerm();
+    Term b = x.eqTerm(y);
+    d_solver.assertFormula(a);
+    Result entailed = d_solver.checkEntailed(a);
+    assertTrue(entailed.isEntailed());
+    assertFalse(entailed.isEntailmentUnknown());
+    Result not_entailed = d_solver.checkEntailed(b);
+    assertTrue(not_entailed.isNotEntailed());
+    assertFalse(not_entailed.isEntailmentUnknown());
+  }
+
+  @Test void isEntailmentUnknown() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_NIA");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("solve-int-as-bv", "32");
+    Sort int_sort = d_solver.getIntegerSort();
+    Term x = d_solver.mkVar(int_sort, "x");
+    d_solver.assertFormula(x.eqTerm(x).notTerm());
+    Result res = d_solver.checkEntailed(x.eqTerm(x));
+    assertFalse(res.isEntailed());
+    assertTrue(res.isEntailmentUnknown());
+    assertEquals(res.getUnknownExplanation(), Result.UnknownExplanation.UNKNOWN_REASON);
+  }
+}
diff --git a/test/unit/api/java/SolverTest.java b/test/unit/api/java/SolverTest.java
new file mode 100644 (file)
index 0000000..8511827
--- /dev/null
@@ -0,0 +1,2559 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Mudathir Mohamed, Andrew Reynolds
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the Solver class of the Java API.
+ */
+
+package tests;
+
+import static io.github.cvc5.api.Kind.*;
+import static io.github.cvc5.api.RoundingMode.*;
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import java.math.BigInteger;
+import java.util.*;
+import java.util.concurrent.atomic.AtomicReference;
+import org.junit.jupiter.api.*;
+import org.junit.jupiter.api.function.Executable;
+
+class SolverTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  @Test void recoverableException() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x).notTerm());
+    assertThrows(CVC5ApiRecoverableException.class, () -> d_solver.getValue(x));
+  }
+
+  @Test void supportsFloatingPoint() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkRoundingMode(ROUND_NEAREST_TIES_TO_EVEN));
+  }
+
+  @Test void getBooleanSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.getBooleanSort());
+  }
+
+  @Test void getIntegerSort()
+  {
+    assertDoesNotThrow(() -> d_solver.getIntegerSort());
+  }
+
+  @Test void getNullSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.getNullSort());
+  }
+
+  @Test void getRealSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.getRealSort());
+  }
+
+  @Test void getRegExpSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.getRegExpSort());
+  }
+
+  @Test void getStringSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.getStringSort());
+  }
+
+  @Test void getRoundingModeSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.getRoundingModeSort());
+  }
+
+  @Test void mkArraySort() throws CVC5ApiException
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort intSort = d_solver.getIntegerSort();
+    Sort realSort = d_solver.getRealSort();
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertDoesNotThrow(() -> d_solver.mkArraySort(boolSort, boolSort));
+    assertDoesNotThrow(() -> d_solver.mkArraySort(intSort, intSort));
+    assertDoesNotThrow(() -> d_solver.mkArraySort(realSort, realSort));
+    assertDoesNotThrow(() -> d_solver.mkArraySort(bvSort, bvSort));
+    assertDoesNotThrow(() -> d_solver.mkArraySort(boolSort, intSort));
+    assertDoesNotThrow(() -> d_solver.mkArraySort(realSort, bvSort));
+
+    Sort fpSort = d_solver.mkFloatingPointSort(3, 5);
+    assertDoesNotThrow(() -> d_solver.mkArraySort(fpSort, fpSort));
+    assertDoesNotThrow(() -> d_solver.mkArraySort(bvSort, fpSort));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkArraySort(boolSort, boolSort));
+  }
+
+  @Test void mkBitVectorSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkBitVectorSort(32));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVectorSort(0));
+  }
+
+  @Test void mkFloatingPointSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkFloatingPointSort(4, 8));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPointSort(0, 8));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPointSort(4, 0));
+  }
+
+  @Test void mkDatatypeSort() throws CVC5ApiException
+  {
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    assertDoesNotThrow(() -> d_solver.mkDatatypeSort(dtypeSpec));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkDatatypeSort(dtypeSpec));
+
+    DatatypeDecl throwsDtypeSpec = d_solver.mkDatatypeDecl("list");
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkDatatypeSort(throwsDtypeSpec));
+  }
+
+  @Test void mkDatatypeSorts() throws CVC5ApiException
+  {
+    Solver slv = new Solver();
+
+    DatatypeDecl dtypeSpec1 = d_solver.mkDatatypeDecl("list1");
+    DatatypeConstructorDecl cons1 = d_solver.mkDatatypeConstructorDecl("cons1");
+    cons1.addSelector("head1", d_solver.getIntegerSort());
+    dtypeSpec1.addConstructor(cons1);
+    DatatypeConstructorDecl nil1 = d_solver.mkDatatypeConstructorDecl("nil1");
+    dtypeSpec1.addConstructor(nil1);
+    DatatypeDecl dtypeSpec2 = d_solver.mkDatatypeDecl("list2");
+    DatatypeConstructorDecl cons2 = d_solver.mkDatatypeConstructorDecl("cons2");
+    cons2.addSelector("head2", d_solver.getIntegerSort());
+    dtypeSpec2.addConstructor(cons2);
+    DatatypeConstructorDecl nil2 = d_solver.mkDatatypeConstructorDecl("nil2");
+    dtypeSpec2.addConstructor(nil2);
+    DatatypeDecl[] decls = {dtypeSpec1, dtypeSpec2};
+    assertDoesNotThrow(() -> d_solver.mkDatatypeSorts(decls));
+
+    assertThrows(CVC5ApiException.class, () -> slv.mkDatatypeSorts(decls));
+
+    DatatypeDecl throwsDtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeDecl[] throwsDecls = new DatatypeDecl[] {throwsDtypeSpec};
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkDatatypeSorts(throwsDecls));
+
+    /* with unresolved sorts */
+    Sort unresList = d_solver.mkUninterpretedSort("ulist");
+    Set<Sort> unresSorts = new HashSet<>();
+    unresSorts.add(unresList);
+    DatatypeDecl ulist = d_solver.mkDatatypeDecl("ulist");
+    DatatypeConstructorDecl ucons = d_solver.mkDatatypeConstructorDecl("ucons");
+    ucons.addSelector("car", unresList);
+    ucons.addSelector("cdr", unresList);
+    ulist.addConstructor(ucons);
+    DatatypeConstructorDecl unil = d_solver.mkDatatypeConstructorDecl("unil");
+    ulist.addConstructor(unil);
+    DatatypeDecl[] udecls = new DatatypeDecl[] {ulist};
+    assertDoesNotThrow(() -> d_solver.mkDatatypeSorts(Arrays.asList(udecls), unresSorts));
+
+    assertThrows(
+        CVC5ApiException.class, () -> slv.mkDatatypeSorts(Arrays.asList(udecls), unresSorts));
+
+    /* Note: More tests are in datatype_api_black. */
+  }
+
+  @Test void mkFunctionSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(()
+                           -> d_solver.mkFunctionSort(
+                               d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort()));
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    // function arguments are allowed
+    assertDoesNotThrow(() -> d_solver.mkFunctionSort(funSort, d_solver.getIntegerSort()));
+    // non-first-class arguments are not allowed
+    Sort reSort = d_solver.getRegExpSort();
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkFunctionSort(reSort, d_solver.getIntegerSort()));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkFunctionSort(d_solver.getIntegerSort(), funSort));
+
+    assertDoesNotThrow(()
+                           -> d_solver.mkFunctionSort(new Sort[] {d_solver.mkUninterpretedSort("u"),
+                                                          d_solver.getIntegerSort()},
+                               d_solver.getIntegerSort()));
+    Sort funSort2 =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    // function arguments are allowed
+    assertDoesNotThrow(
+        ()
+            -> d_solver.mkFunctionSort(new Sort[] {funSort2, d_solver.mkUninterpretedSort("u")},
+                d_solver.getIntegerSort()));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.mkFunctionSort(
+                new Sort[] {d_solver.getIntegerSort(), d_solver.mkUninterpretedSort("u")},
+                funSort2));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class,
+        () -> slv.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort()));
+
+    assertThrows(CVC5ApiException.class,
+        () -> slv.mkFunctionSort(slv.mkUninterpretedSort("u"), d_solver.getIntegerSort()));
+
+    Sort[] sorts1 =
+        new Sort[] {d_solver.getBooleanSort(), slv.getIntegerSort(), d_solver.getIntegerSort()};
+    Sort[] sorts2 = new Sort[] {slv.getBooleanSort(), slv.getIntegerSort()};
+    assertDoesNotThrow(() -> slv.mkFunctionSort(sorts2, slv.getIntegerSort()));
+    assertThrows(CVC5ApiException.class, () -> slv.mkFunctionSort(sorts1, slv.getIntegerSort()));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.mkFunctionSort(sorts2, d_solver.getIntegerSort()));
+  }
+
+  @Test void mkParamSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkParamSort("T"));
+    assertDoesNotThrow(() -> d_solver.mkParamSort(""));
+  }
+
+  @Test void mkPredicateSort()
+  {
+    assertDoesNotThrow(() -> d_solver.mkPredicateSort(new Sort[] {d_solver.getIntegerSort()}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkPredicateSort(new Sort[] {}));
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    // functions as arguments are allowed
+    assertDoesNotThrow(
+        () -> d_solver.mkPredicateSort(new Sort[] {d_solver.getIntegerSort(), funSort}));
+
+    Solver slv = new Solver();
+    assertThrows(
+        CVC5ApiException.class, () -> slv.mkPredicateSort(new Sort[] {d_solver.getIntegerSort()}));
+  }
+
+  @Test void mkRecordSort() throws CVC5ApiException
+  {
+    Pair<String, Sort>[] fields = new Pair[] {new Pair<>("b", d_solver.getBooleanSort()),
+        new Pair<>("bv", d_solver.mkBitVectorSort(8)),
+        new Pair<>("i", d_solver.getIntegerSort())};
+    Pair<String, Sort>[] empty = new Pair[0];
+    assertDoesNotThrow(() -> d_solver.mkRecordSort(fields));
+    assertDoesNotThrow(() -> d_solver.mkRecordSort(empty));
+    Sort recSort = d_solver.mkRecordSort(fields);
+    assertDoesNotThrow(() -> recSort.getDatatype());
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkRecordSort(fields));
+  }
+
+  @Test void mkSetSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkSetSort(d_solver.getBooleanSort()));
+    assertDoesNotThrow(() -> d_solver.mkSetSort(d_solver.getIntegerSort()));
+    assertDoesNotThrow(() -> d_solver.mkSetSort(d_solver.mkBitVectorSort(4)));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkSetSort(d_solver.mkBitVectorSort(4)));
+  }
+
+  @Test void mkBagSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkBagSort(d_solver.getBooleanSort()));
+    assertDoesNotThrow(() -> d_solver.mkBagSort(d_solver.getIntegerSort()));
+    assertDoesNotThrow(() -> d_solver.mkBagSort(d_solver.mkBitVectorSort(4)));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkBagSort(d_solver.mkBitVectorSort(4)));
+  }
+
+  @Test void mkSequenceSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkSequenceSort(d_solver.getBooleanSort()));
+    assertDoesNotThrow(
+        () -> d_solver.mkSequenceSort(d_solver.mkSequenceSort(d_solver.getIntegerSort())));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkSequenceSort(d_solver.getIntegerSort()));
+  }
+
+  @Test void mkUninterpretedSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkUninterpretedSort("u"));
+    assertDoesNotThrow(() -> d_solver.mkUninterpretedSort(""));
+  }
+
+  @Test void mkSortConstructorSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkSortConstructorSort("s", 2));
+    assertDoesNotThrow(() -> d_solver.mkSortConstructorSort("", 2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkSortConstructorSort("", 0));
+  }
+
+  @Test void mkTupleSort() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort()}));
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort(), funSort}));
+
+    Solver slv = new Solver();
+    assertThrows(
+        CVC5ApiException.class, () -> slv.mkTupleSort(new Sort[] {d_solver.getIntegerSort()}));
+  }
+
+  @Test void mkBitVector() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, 2));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(32, 2));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "-1111111", 2));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "0101", 2));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "00000101", 2));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "-127", 10));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "255", 10));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "-7f", 16));
+    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "a0", 16));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(0, 2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(0, "-127", 10));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(0, "a0", 16));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "", 2));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "101", 5));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "128", 11));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "a0", 21));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-11111111", 2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "101010101", 2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-256", 10));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "257", 10));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-a0", 16));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "fffff", 16));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "10201010", 2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-25x", 10));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "2x7", 10));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "fzff", 16));
+
+    assertEquals(d_solver.mkBitVector(8, "0101", 2), d_solver.mkBitVector(8, "00000101", 2));
+    assertEquals(d_solver.mkBitVector(4, "-1", 2), d_solver.mkBitVector(4, "1111", 2));
+    assertEquals(d_solver.mkBitVector(4, "-1", 16), d_solver.mkBitVector(4, "1111", 2));
+    assertEquals(d_solver.mkBitVector(4, "-1", 10), d_solver.mkBitVector(4, "1111", 2));
+    assertEquals(d_solver.mkBitVector(8, "01010101", 2).toString(), "#b01010101");
+    assertEquals(d_solver.mkBitVector(8, "F", 16).toString(), "#b00001111");
+    assertEquals(d_solver.mkBitVector(8, "-1", 10), d_solver.mkBitVector(8, "FF", 16));
+  }
+
+  @Test void mkVar() throws CVC5ApiException
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort intSort = d_solver.getIntegerSort();
+    Sort funSort = d_solver.mkFunctionSort(intSort, boolSort);
+    assertDoesNotThrow(() -> d_solver.mkVar(boolSort));
+    assertDoesNotThrow(() -> d_solver.mkVar(funSort));
+    assertDoesNotThrow(() -> d_solver.mkVar(boolSort, ("b")));
+    assertDoesNotThrow(() -> d_solver.mkVar(funSort, ""));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkVar(d_solver.getNullSort()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkVar(d_solver.getNullSort(), "a"));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkVar(boolSort, "x"));
+  }
+
+  @Test void mkBoolean() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkBoolean(true));
+    assertDoesNotThrow(() -> d_solver.mkBoolean(false));
+  }
+
+  @Test void mkRoundingMode() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkRoundingMode(RoundingMode.ROUND_TOWARD_ZERO));
+  }
+
+  @Test void mkUninterpretedConst() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkUninterpretedConst(d_solver.getBooleanSort(), 1));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkUninterpretedConst(d_solver.getNullSort(), 1));
+    Solver slv = new Solver();
+    assertThrows(
+        CVC5ApiException.class, () -> slv.mkUninterpretedConst(d_solver.getBooleanSort(), 1));
+  }
+
+  @Test void mkAbstractValue() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkAbstractValue(("1")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(("0")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(("-1")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(("1.2")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue("1/2"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue("asdf"));
+
+    assertDoesNotThrow(() -> d_solver.mkAbstractValue((int) 1));
+    assertDoesNotThrow(() -> d_solver.mkAbstractValue((int) 1));
+    assertDoesNotThrow(() -> d_solver.mkAbstractValue((long) 1));
+    assertDoesNotThrow(() -> d_solver.mkAbstractValue((long) 1));
+    // java does not have specific types for unsigned integers, therefore the two lines below do not
+    // make sense in java. assertDoesNotThrow(() -> d_solver.mkAbstractValue((int)-1));
+    // assertDoesNotThrow(() -> d_solver.mkAbstractValue((long)-1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(0));
+  }
+
+  @Test void mkFloatingPoint() throws CVC5ApiException
+  {
+    Term t1 = d_solver.mkBitVector(8);
+    Term t2 = d_solver.mkBitVector(4);
+    Term t3 = d_solver.mkInteger(2);
+    assertDoesNotThrow(() -> d_solver.mkFloatingPoint(3, 5, t1));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkFloatingPoint(0, 5, d_solver.getNullTerm()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(0, 5, t1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(3, 0, t1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(3, 5, t2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(3, 5, t2));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkFloatingPoint(3, 5, t1));
+  }
+
+  @Test void mkEmptySet() throws CVC5ApiException
+  {
+    Solver slv = new Solver();
+    Sort s = d_solver.mkSetSort(d_solver.getBooleanSort());
+    assertDoesNotThrow(() -> d_solver.mkEmptySet(d_solver.getNullSort()));
+    assertDoesNotThrow(() -> d_solver.mkEmptySet(s));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkEmptySet(d_solver.getBooleanSort()));
+    assertThrows(CVC5ApiException.class, () -> slv.mkEmptySet(s));
+  }
+
+  @Test void mkEmptyBag() throws CVC5ApiException
+  {
+    Solver slv = new Solver();
+    Sort s = d_solver.mkBagSort(d_solver.getBooleanSort());
+    assertDoesNotThrow(() -> d_solver.mkEmptyBag(d_solver.getNullSort()));
+    assertDoesNotThrow(() -> d_solver.mkEmptyBag(s));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkEmptyBag(d_solver.getBooleanSort()));
+
+    assertThrows(CVC5ApiException.class, () -> slv.mkEmptyBag(s));
+  }
+
+  @Test void mkEmptySequence() throws CVC5ApiException
+  {
+    Solver slv = new Solver();
+    Sort s = d_solver.mkSequenceSort(d_solver.getBooleanSort());
+    assertDoesNotThrow(() -> d_solver.mkEmptySequence(s));
+    assertDoesNotThrow(() -> d_solver.mkEmptySequence(d_solver.getBooleanSort()));
+    assertThrows(CVC5ApiException.class, () -> slv.mkEmptySequence(s));
+  }
+
+  @Test void mkFalse() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkFalse());
+    assertDoesNotThrow(() -> d_solver.mkFalse());
+  }
+
+  @Test void mkNaN() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkNaN(3, 5));
+  }
+
+  @Test void mkNegZero() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.mkNegZero(3, 5));
+  }
+
+  @Test void mkNegInf()
+  {
+    assertDoesNotThrow(() -> d_solver.mkNegInf(3, 5));
+  }
+
+  @Test void mkPosInf()
+  {
+    assertDoesNotThrow(() -> d_solver.mkPosInf(3, 5));
+  }
+
+  @Test void mkPosZero()
+  {
+    assertDoesNotThrow(() -> d_solver.mkPosZero(3, 5));
+  }
+
+  @Test void mkOp()
+  {
+    // Unlike c++,  mkOp(Kind kind, Kind k) is a type error in java
+    // assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT, EQUAL));
+
+    // mkOp(Kind kind, const std::string& arg)
+    assertDoesNotThrow(() -> d_solver.mkOp(DIVISIBLE, "2147483648"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT, "asdf"));
+
+    // mkOp(Kind kind, int arg)
+    assertDoesNotThrow(() -> d_solver.mkOp(DIVISIBLE, 1));
+    assertDoesNotThrow(() -> d_solver.mkOp(BITVECTOR_ROTATE_LEFT, 1));
+    assertDoesNotThrow(() -> d_solver.mkOp(BITVECTOR_ROTATE_RIGHT, 1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT, 1));
+
+    // mkOp(Kind kind, int arg1, int arg2)
+    assertDoesNotThrow(() -> d_solver.mkOp(BITVECTOR_EXTRACT, 1, 1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(DIVISIBLE, 1, 2));
+
+    // mkOp(Kind kind, int[] args)
+    int[] args = new int[] {1, 2, 2};
+    assertDoesNotThrow(() -> d_solver.mkOp(TUPLE_PROJECT, args));
+  }
+
+  @Test void mkPi()
+  {
+    assertDoesNotThrow(() -> d_solver.mkPi());
+  }
+
+  @Test void mkInteger()
+  {
+    assertDoesNotThrow(() -> d_solver.mkInteger("123"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("1.23"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("1/23"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("12/3"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(".2"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("2."));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(""));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("asdf"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("1.2/3"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("."));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("/"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("2/"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("/2"));
+
+    assertDoesNotThrow(() -> d_solver.mkReal(("123")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("1.23")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("1/23")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("12/3")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger((".2")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("2.")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("asdf")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("1.2/3")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger((".")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("/")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("2/")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("/2")));
+
+    int val1 = 1;
+    long val2 = -1;
+    int val3 = 1;
+    long val4 = -1;
+    assertDoesNotThrow(() -> d_solver.mkInteger(val1));
+    assertDoesNotThrow(() -> d_solver.mkInteger(val2));
+    assertDoesNotThrow(() -> d_solver.mkInteger(val3));
+    assertDoesNotThrow(() -> d_solver.mkInteger(val4));
+    assertDoesNotThrow(() -> d_solver.mkInteger(val4));
+  }
+
+  @Test void mkReal()
+  {
+    assertDoesNotThrow(() -> d_solver.mkReal("123"));
+    assertDoesNotThrow(() -> d_solver.mkReal("1.23"));
+    assertDoesNotThrow(() -> d_solver.mkReal("1/23"));
+    assertDoesNotThrow(() -> d_solver.mkReal("12/3"));
+    assertDoesNotThrow(() -> d_solver.mkReal(".2"));
+    assertDoesNotThrow(() -> d_solver.mkReal("2."));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(""));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("asdf"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("1.2/3"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("."));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("/"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("2/"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("/2"));
+
+    assertDoesNotThrow(() -> d_solver.mkReal(("123")));
+    assertDoesNotThrow(() -> d_solver.mkReal(("1.23")));
+    assertDoesNotThrow(() -> d_solver.mkReal(("1/23")));
+    assertDoesNotThrow(() -> d_solver.mkReal(("12/3")));
+    assertDoesNotThrow(() -> d_solver.mkReal((".2")));
+    assertDoesNotThrow(() -> d_solver.mkReal(("2.")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("asdf")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("1.2/3")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal((".")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("/")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("2/")));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("/2")));
+
+    int val1 = 1;
+    long val2 = -1;
+    int val3 = 1;
+    long val4 = -1;
+    assertDoesNotThrow(() -> d_solver.mkReal(val1));
+    assertDoesNotThrow(() -> d_solver.mkReal(val2));
+    assertDoesNotThrow(() -> d_solver.mkReal(val3));
+    assertDoesNotThrow(() -> d_solver.mkReal(val4));
+    assertDoesNotThrow(() -> d_solver.mkReal(val4));
+    assertDoesNotThrow(() -> d_solver.mkReal(val1, val1));
+    assertDoesNotThrow(() -> d_solver.mkReal(val2, val2));
+    assertDoesNotThrow(() -> d_solver.mkReal(val3, val3));
+    assertDoesNotThrow(() -> d_solver.mkReal(val4, val4));
+  }
+
+  @Test void mkRegexpEmpty()
+  {
+    Sort strSort = d_solver.getStringSort();
+    Term s = d_solver.mkConst(strSort, "s");
+    assertDoesNotThrow(() -> d_solver.mkTerm(STRING_IN_REGEXP, s, d_solver.mkRegexpEmpty()));
+  }
+
+  @Test void mkRegexpSigma()
+  {
+    Sort strSort = d_solver.getStringSort();
+    Term s = d_solver.mkConst(strSort, "s");
+    assertDoesNotThrow(() -> d_solver.mkTerm(STRING_IN_REGEXP, s, d_solver.mkRegexpSigma()));
+  }
+
+  @Test void mkSepEmp()
+  {
+    assertDoesNotThrow(() -> d_solver.mkSepEmp());
+  }
+
+  @Test void mkSepNil()
+  {
+    assertDoesNotThrow(() -> d_solver.mkSepNil(d_solver.getBooleanSort()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkSepNil(d_solver.getNullSort()));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkSepNil(d_solver.getIntegerSort()));
+  }
+
+  @Test void mkString()
+  {
+    assertDoesNotThrow(() -> d_solver.mkString(""));
+    assertDoesNotThrow(() -> d_solver.mkString("asdfasdf"));
+    assertEquals(d_solver.mkString("asdf\\nasdf").toString(), "\"asdf\\u{5c}nasdf\"");
+    assertEquals(d_solver.mkString("asdf\\u{005c}nasdf", true).toString(), "\"asdf\\u{5c}nasdf\"");
+  }
+
+  @Test void mkTerm() throws CVC5ApiException
+  {
+    Sort bv32 = d_solver.mkBitVectorSort(32);
+    Term a = d_solver.mkConst(bv32, "a");
+    Term b = d_solver.mkConst(bv32, "b");
+    Term[] v1 = new Term[] {a, b};
+    Term[] v2 = new Term[] {a, d_solver.getNullTerm()};
+    Term[] v3 = new Term[] {a, d_solver.mkTrue()};
+    Term[] v4 = new Term[] {d_solver.mkInteger(1), d_solver.mkInteger(2)};
+    Term[] v5 = new Term[] {d_solver.mkInteger(1), d_solver.getNullTerm()};
+    Term[] v6 = new Term[] {};
+    Solver slv = new Solver();
+
+    // mkTerm(Kind kind) const
+    assertDoesNotThrow(() -> d_solver.mkTerm(PI));
+    assertDoesNotThrow(() -> d_solver.mkTerm(REGEXP_EMPTY));
+    assertDoesNotThrow(() -> d_solver.mkTerm(REGEXP_SIGMA));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(CONST_BITVECTOR));
+
+    // mkTerm(Kind kind, Term child) const
+    assertDoesNotThrow(() -> d_solver.mkTerm(NOT, d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(NOT, d_solver.getNullTerm()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(NOT, a));
+    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(NOT, d_solver.mkTrue()));
+
+    // mkTerm(Kind kind, Term child1, Term child2) const
+    assertDoesNotThrow(() -> d_solver.mkTerm(EQUAL, a, b));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, d_solver.getNullTerm(), b));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, a, d_solver.getNullTerm()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, a, d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(EQUAL, a, b));
+
+    // mkTerm(Kind kind, Term child1, Term child2, Term child3) const
+    assertDoesNotThrow(
+        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(ITE, d_solver.getNullTerm(), d_solver.mkTrue(), d_solver.mkTrue()));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.getNullTerm(), d_solver.mkTrue()));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), d_solver.getNullTerm()));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), b));
+
+    assertThrows(CVC5ApiException.class,
+        () -> slv.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), d_solver.mkTrue()));
+
+    // mkTerm(Kind kind, const Term[]& children) const
+    assertDoesNotThrow(() -> d_solver.mkTerm(EQUAL, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, v2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, v3));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(DISTINCT, v6));
+  }
+
+  @Test void mkTermFromOp() throws CVC5ApiException
+  {
+    Sort bv32 = d_solver.mkBitVectorSort(32);
+    Term a = d_solver.mkConst(bv32, "a");
+    Term b = d_solver.mkConst(bv32, "b");
+    Term[] v1 = new Term[] {d_solver.mkInteger(1), d_solver.mkInteger(2)};
+    Term[] v2 = new Term[] {d_solver.mkInteger(1), d_solver.getNullTerm()};
+    Term[] v3 = new Term[] {};
+    Term[] v4 = new Term[] {d_solver.mkInteger(5)};
+    Solver slv = new Solver();
+
+    // simple operator terms
+    Op opterm1 = d_solver.mkOp(BITVECTOR_EXTRACT, 2, 1);
+    Op opterm2 = d_solver.mkOp(DIVISIBLE, 1);
+
+    // list datatype
+    Sort sort = d_solver.mkParamSort("T");
+    DatatypeDecl listDecl = d_solver.mkDatatypeDecl("paramlist", sort);
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    cons.addSelector("head", sort);
+    cons.addSelectorSelf("tail");
+    listDecl.addConstructor(cons);
+    listDecl.addConstructor(nil);
+    Sort listSort = d_solver.mkDatatypeSort(listDecl);
+    Sort intListSort = listSort.instantiate(new Sort[] {d_solver.getIntegerSort()});
+    Term c = d_solver.mkConst(intListSort, "c");
+    Datatype list = listSort.getDatatype();
+
+    // list datatype constructor and selector operator terms
+    Term consTerm1 = list.getConstructorTerm("cons");
+    Term consTerm2 = list.getConstructor("cons").getConstructorTerm();
+    Term nilTerm1 = list.getConstructorTerm("nil");
+    Term nilTerm2 = list.getConstructor("nil").getConstructorTerm();
+    Term headTerm1 = list.getConstructor("cons").getSelectorTerm("head");
+    Term headTerm2 = list.getConstructor("cons").getSelector("head").getSelectorTerm();
+    Term tailTerm1 = list.getConstructor("cons").getSelectorTerm("tail");
+    Term tailTerm2 = list.getConstructor("cons").getSelector("tail").getSelectorTerm();
+
+    // mkTerm(Op op, Term term) const
+    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm1));
+    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_SELECTOR, nilTerm1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_SELECTOR, consTerm1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_CONSTRUCTOR, consTerm2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_SELECTOR, headTerm1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1));
+    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(APPLY_CONSTRUCTOR, nilTerm1));
+
+    // mkTerm(Op op, Term child) const
+    assertDoesNotThrow(() -> d_solver.mkTerm(opterm1, a));
+    assertDoesNotThrow(() -> d_solver.mkTerm(opterm2, d_solver.mkInteger(1)));
+    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_SELECTOR, headTerm1, c));
+    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_SELECTOR, tailTerm2, c));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, a));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1, d_solver.getNullTerm()));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(APPLY_CONSTRUCTOR, consTerm1, d_solver.mkInteger(0)));
+
+    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(opterm1, a));
+
+    // mkTerm(Op op, Term child1, Term child2) const
+    assertDoesNotThrow(()
+                           -> d_solver.mkTerm(APPLY_CONSTRUCTOR,
+                               consTerm1,
+                               d_solver.mkInteger(0),
+                               d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm1)));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(opterm2, d_solver.mkInteger(1), d_solver.mkInteger(2)));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1, a, b));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(opterm2, d_solver.mkInteger(1), d_solver.getNullTerm()));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(opterm2, d_solver.getNullTerm(), d_solver.mkInteger(1)));
+
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.mkTerm(APPLY_CONSTRUCTOR,
+                consTerm1,
+                d_solver.mkInteger(0),
+                d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm1)));
+
+    // mkTerm(Op op, Term child1, Term child2, Term child3) const
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1, a, b, a));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.mkTerm(
+                opterm2, d_solver.mkInteger(1), d_solver.mkInteger(1), d_solver.getNullTerm()));
+
+    // mkTerm(Op op, Term[] children)
+    assertDoesNotThrow(() -> d_solver.mkTerm(opterm2, v4));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, v2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, v3));
+    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(opterm2, v4));
+  }
+
+  @Test void mkTrue()
+  {
+    assertDoesNotThrow(() -> d_solver.mkTrue());
+    assertDoesNotThrow(() -> d_solver.mkTrue());
+  }
+
+  @Test void mkTuple()
+  {
+    assertDoesNotThrow(()
+                           -> d_solver.mkTuple(new Sort[] {d_solver.mkBitVectorSort(3)},
+                               new Term[] {d_solver.mkBitVector(3, "101", 2)}));
+    assertDoesNotThrow(()
+                           -> d_solver.mkTuple(new Sort[] {d_solver.getRealSort()},
+                               new Term[] {d_solver.mkInteger("5")}));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTuple(new Sort[] {}, new Term[] {d_solver.mkBitVector(3, "101", 2)}));
+
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.mkTuple(new Sort[] {d_solver.mkBitVectorSort(4)},
+                new Term[] {d_solver.mkBitVector(3, "101", 2)}));
+
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.mkTuple(
+                new Sort[] {d_solver.getIntegerSort()}, new Term[] {d_solver.mkReal("5.3")}));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.mkTuple(new Sort[] {d_solver.mkBitVectorSort(3)},
+                new Term[] {slv.mkBitVector(3, "101", 2)}));
+
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.mkTuple(new Sort[] {slv.mkBitVectorSort(3)},
+                new Term[] {d_solver.mkBitVector(3, "101", 2)}));
+  }
+
+  @Test void mkUniverseSet()
+  {
+    assertDoesNotThrow(() -> d_solver.mkUniverseSet(d_solver.getBooleanSort()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkUniverseSet(d_solver.getNullSort()));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkUniverseSet(d_solver.getBooleanSort()));
+  }
+
+  @Test void mkConst()
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort intSort = d_solver.getIntegerSort();
+    Sort funSort = d_solver.mkFunctionSort(intSort, boolSort);
+    assertDoesNotThrow(() -> d_solver.mkConst(boolSort));
+    assertDoesNotThrow(() -> d_solver.mkConst(funSort));
+    assertDoesNotThrow(() -> d_solver.mkConst(boolSort, ("b")));
+    assertDoesNotThrow(() -> d_solver.mkConst(intSort, ("i")));
+    assertDoesNotThrow(() -> d_solver.mkConst(funSort, "f"));
+    assertDoesNotThrow(() -> d_solver.mkConst(funSort, ""));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkConst(d_solver.getNullSort()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkConst(d_solver.getNullSort(), "a"));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkConst(boolSort));
+  }
+
+  @Test void mkConstArray()
+  {
+    Sort intSort = d_solver.getIntegerSort();
+    Sort arrSort = d_solver.mkArraySort(intSort, intSort);
+    Term zero = d_solver.mkInteger(0);
+    Term constArr = d_solver.mkConstArray(arrSort, zero);
+
+    assertDoesNotThrow(() -> d_solver.mkConstArray(arrSort, zero));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkConstArray(d_solver.getNullSort(), zero));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkConstArray(arrSort, d_solver.getNullTerm()));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkConstArray(arrSort, d_solver.mkBitVector(1, 1)));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkConstArray(intSort, zero));
+    Solver slv = new Solver();
+    Term zero2 = slv.mkInteger(0);
+    Sort arrSort2 = slv.mkArraySort(slv.getIntegerSort(), slv.getIntegerSort());
+    assertThrows(CVC5ApiException.class, () -> slv.mkConstArray(arrSort2, zero));
+    assertThrows(CVC5ApiException.class, () -> slv.mkConstArray(arrSort, zero2));
+  }
+
+  @Test void declareDatatype()
+  {
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    DatatypeConstructorDecl[] ctors1 = new DatatypeConstructorDecl[] {nil};
+    assertDoesNotThrow(() -> d_solver.declareDatatype(("a"), ctors1));
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    DatatypeConstructorDecl nil2 = d_solver.mkDatatypeConstructorDecl("nil");
+    DatatypeConstructorDecl[] ctors2 = new DatatypeConstructorDecl[] {cons, nil2};
+    assertDoesNotThrow(() -> d_solver.declareDatatype(("b"), ctors2));
+    DatatypeConstructorDecl cons2 = d_solver.mkDatatypeConstructorDecl("cons");
+    DatatypeConstructorDecl nil3 = d_solver.mkDatatypeConstructorDecl("nil");
+    DatatypeConstructorDecl[] ctors3 = new DatatypeConstructorDecl[] {cons2, nil3};
+    assertDoesNotThrow(() -> d_solver.declareDatatype((""), ctors3));
+    DatatypeConstructorDecl[] ctors4 = new DatatypeConstructorDecl[0];
+    assertThrows(CVC5ApiException.class, () -> d_solver.declareDatatype(("c"), ctors4));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.declareDatatype((""), ctors4));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.declareDatatype(("a"), ctors1));
+  }
+
+  @Test void declareFun() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    assertDoesNotThrow(() -> d_solver.declareFun("f1", new Sort[] {}, bvSort));
+    assertDoesNotThrow(
+        () -> d_solver.declareFun("f3", new Sort[] {bvSort, d_solver.getIntegerSort()}, bvSort));
+    assertThrows(CVC5ApiException.class, () -> d_solver.declareFun("f2", new Sort[] {}, funSort));
+    // functions as arguments is allowed
+    assertDoesNotThrow(() -> d_solver.declareFun("f4", new Sort[] {bvSort, funSort}, bvSort));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.declareFun("f5", new Sort[] {bvSort, bvSort}, funSort));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.declareFun("f1", new Sort[] {}, bvSort));
+  }
+
+  @Test void declareSort()
+  {
+    assertDoesNotThrow(() -> d_solver.declareSort("s", 0));
+    assertDoesNotThrow(() -> d_solver.declareSort("s", 2));
+    assertDoesNotThrow(() -> d_solver.declareSort("", 2));
+  }
+
+  @Test void defineSort()
+  {
+    Sort sortVar0 = d_solver.mkParamSort("T0");
+    Sort sortVar1 = d_solver.mkParamSort("T1");
+    Sort intSort = d_solver.getIntegerSort();
+    Sort realSort = d_solver.getRealSort();
+    Sort arraySort0 = d_solver.mkArraySort(sortVar0, sortVar0);
+    Sort arraySort1 = d_solver.mkArraySort(sortVar0, sortVar1);
+    // Now create instantiations of the defined sorts
+    assertDoesNotThrow(() -> arraySort0.substitute(sortVar0, intSort));
+    assertDoesNotThrow(()
+                           -> arraySort1.substitute(
+                               new Sort[] {sortVar0, sortVar1}, new Sort[] {intSort, realSort}));
+  }
+
+  @Test void defineFun() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
+    Sort funSort2 =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    Term b1 = d_solver.mkVar(bvSort, "b1");
+    Term b11 = d_solver.mkVar(bvSort, "b1");
+    Term b2 = d_solver.mkVar(d_solver.getIntegerSort(), "b2");
+    Term b3 = d_solver.mkVar(funSort2, "b3");
+    Term v1 = d_solver.mkConst(bvSort, "v1");
+    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
+    Term v3 = d_solver.mkConst(funSort2, "v3");
+    Term f1 = d_solver.mkConst(funSort1, "f1");
+    Term f2 = d_solver.mkConst(funSort2, "f2");
+    Term f3 = d_solver.mkConst(bvSort, "f3");
+    assertDoesNotThrow(() -> d_solver.defineFun("f", new Term[] {}, bvSort, v1));
+    assertDoesNotThrow(() -> d_solver.defineFun("ff", new Term[] {b1, b2}, bvSort, v1));
+    assertDoesNotThrow(() -> d_solver.defineFun(f1, new Term[] {b1, b11}, v1));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFun("ff", new Term[] {v1, b2}, bvSort, v1));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFun("fff", new Term[] {b1}, bvSort, v3));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFun("ffff", new Term[] {b1}, funSort2, v3));
+
+    // b3 has function sort, which is allowed as an argument
+    assertDoesNotThrow(() -> d_solver.defineFun("fffff", new Term[] {b1, b3}, bvSort, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {v1, b11}, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {b1}, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {b1, b11}, v2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {b1, b11}, v3));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f2, new Term[] {b1}, v2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f3, new Term[] {b1}, v1));
+
+    Solver slv = new Solver();
+    Sort bvSort2 = slv.mkBitVectorSort(32);
+    Term v12 = slv.mkConst(bvSort2, "v1");
+    Term b12 = slv.mkVar(bvSort2, "b1");
+    Term b22 = slv.mkVar(slv.getIntegerSort(), "b2");
+    assertThrows(CVC5ApiException.class, () -> slv.defineFun("f", new Term[] {}, bvSort, v12));
+    assertThrows(CVC5ApiException.class, () -> slv.defineFun("f", new Term[] {}, bvSort2, v1));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b1, b22}, bvSort2, v12));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b12, b2}, bvSort2, v12));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b12, b22}, bvSort, v12));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b12, b22}, bvSort2, v1));
+  }
+
+  @Test void defineFunGlobal()
+  {
+    Sort bSort = d_solver.getBooleanSort();
+    Sort fSort = d_solver.mkFunctionSort(bSort, bSort);
+
+    Term bTrue = d_solver.mkBoolean(true);
+    // (define-fun f () Bool true)
+    Term f = d_solver.defineFun("f", new Term[] {}, bSort, bTrue, true);
+    Term b = d_solver.mkVar(bSort, "b");
+    Term gSym = d_solver.mkConst(fSort, "g");
+    // (define-fun g (b Bool) Bool b)
+    Term g = d_solver.defineFun(gSym, new Term[] {b}, b, true);
+
+    // (assert (or (not f) (not (g true))))
+    d_solver.assertFormula(
+        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
+    assertTrue(d_solver.checkSat().isUnsat());
+    d_solver.resetAssertions();
+    // (assert (or (not f) (not (g true))))
+    d_solver.assertFormula(
+        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
+    assertTrue(d_solver.checkSat().isUnsat());
+  }
+
+  @Test void defineFunRec() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
+    Sort funSort2 =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    Term b1 = d_solver.mkVar(bvSort, "b1");
+    Term b11 = d_solver.mkVar(bvSort, "b1");
+    Term b2 = d_solver.mkVar(d_solver.getIntegerSort(), "b2");
+    Term b3 = d_solver.mkVar(funSort2, "b3");
+    Term v1 = d_solver.mkConst(bvSort, "v1");
+    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
+    Term v3 = d_solver.mkConst(funSort2, "v3");
+    Term f1 = d_solver.mkConst(funSort1, "f1");
+    Term f2 = d_solver.mkConst(funSort2, "f2");
+    Term f3 = d_solver.mkConst(bvSort, "f3");
+    assertDoesNotThrow(() -> d_solver.defineFunRec("f", new Term[] {}, bvSort, v1));
+    assertDoesNotThrow(() -> d_solver.defineFunRec("ff", new Term[] {b1, b2}, bvSort, v1));
+    assertDoesNotThrow(() -> d_solver.defineFunRec(f1, new Term[] {b1, b11}, v1));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFunRec("fff", new Term[] {b1}, bvSort, v3));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFunRec("ff", new Term[] {b1, v2}, bvSort, v1));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFunRec("ffff", new Term[] {b1}, funSort2, v3));
+
+    // b3 has function sort, which is allowed as an argument
+    assertDoesNotThrow(() -> d_solver.defineFunRec("fffff", new Term[] {b1, b3}, bvSort, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f1, new Term[] {b1}, v1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f1, new Term[] {b1, b11}, v2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f1, new Term[] {b1, b11}, v3));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f2, new Term[] {b1}, v2));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f3, new Term[] {b1}, v1));
+
+    Solver slv = new Solver();
+    Sort bvSort2 = slv.mkBitVectorSort(32);
+    Term v12 = slv.mkConst(bvSort2, "v1");
+    Term b12 = slv.mkVar(bvSort2, "b1");
+    Term b22 = slv.mkVar(slv.getIntegerSort(), "b2");
+    assertDoesNotThrow(() -> slv.defineFunRec("f", new Term[] {}, bvSort2, v12));
+    assertDoesNotThrow(() -> slv.defineFunRec("ff", new Term[] {b12, b22}, bvSort2, v12));
+    assertThrows(CVC5ApiException.class, () -> slv.defineFunRec("f", new Term[] {}, bvSort, v12));
+    assertThrows(CVC5ApiException.class, () -> slv.defineFunRec("f", new Term[] {}, bvSort2, v1));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b1, b22}, bvSort2, v12));
+
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b12, b2}, bvSort2, v12));
+
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b12, b22}, bvSort, v12));
+
+    assertThrows(
+        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b12, b22}, bvSort2, v1));
+  }
+
+  @Test void defineFunRecWrongLogic() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_BV");
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort funSort = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
+    Term b = d_solver.mkVar(bvSort, "b");
+    Term v = d_solver.mkConst(bvSort, "v");
+    Term f = d_solver.mkConst(funSort, "f");
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.defineFunRec("f", new Term[] {}, bvSort, v));
+    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f, new Term[] {b, b}, v));
+  }
+
+  @Test void defineFunRecGlobal() throws CVC5ApiException
+  {
+    Sort bSort = d_solver.getBooleanSort();
+    Sort fSort = d_solver.mkFunctionSort(bSort, bSort);
+
+    d_solver.push();
+    Term bTrue = d_solver.mkBoolean(true);
+    // (define-fun f () Bool true)
+    Term f = d_solver.defineFunRec("f", new Term[] {}, bSort, bTrue, true);
+    Term b = d_solver.mkVar(bSort, "b");
+    Term gSym = d_solver.mkConst(fSort, "g");
+    // (define-fun g (b Bool) Bool b)
+    Term g = d_solver.defineFunRec(gSym, new Term[] {b}, b, true);
+
+    // (assert (or (not f) (not (g true))))
+    d_solver.assertFormula(
+        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
+    assertTrue(d_solver.checkSat().isUnsat());
+    d_solver.pop();
+    // (assert (or (not f) (not (g true))))
+    d_solver.assertFormula(
+        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
+    assertTrue(d_solver.checkSat().isUnsat());
+  }
+
+  @Test void defineFunsRec() throws CVC5ApiException
+  {
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
+    Sort funSort2 = d_solver.mkFunctionSort(uSort, d_solver.getIntegerSort());
+    Term b1 = d_solver.mkVar(bvSort, "b1");
+    Term b11 = d_solver.mkVar(bvSort, "b1");
+    Term b2 = d_solver.mkVar(d_solver.getIntegerSort(), "b2");
+    Term b3 = d_solver.mkVar(funSort2, "b3");
+    Term b4 = d_solver.mkVar(uSort, "b4");
+    Term v1 = d_solver.mkConst(bvSort, "v1");
+    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
+    Term v3 = d_solver.mkConst(funSort2, "v3");
+    Term v4 = d_solver.mkConst(uSort, "v4");
+    Term f1 = d_solver.mkConst(funSort1, "f1");
+    Term f2 = d_solver.mkConst(funSort2, "f2");
+    Term f3 = d_solver.mkConst(bvSort, "f3");
+    assertDoesNotThrow(
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f2}, new Term[][] {{b1, b11}, {b4}}, new Term[] {v1, v2}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f2}, new Term[][] {{v1, b11}, {b4}}, new Term[] {v1, v2}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f3}, new Term[][] {{b1, b11}, {b4}}, new Term[] {v1, v2}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f2}, new Term[][] {{b1}, {b4}}, new Term[] {v1, v2}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f2}, new Term[][] {{b1, b2}, {b4}}, new Term[] {v1, v2}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f2}, new Term[][] {{b1, b11}, {b4}}, new Term[] {v1, v4}));
+
+    Solver slv = new Solver();
+    Sort uSort2 = slv.mkUninterpretedSort("u");
+    Sort bvSort2 = slv.mkBitVectorSort(32);
+    Sort funSort12 = slv.mkFunctionSort(new Sort[] {bvSort2, bvSort2}, bvSort2);
+    Sort funSort22 = slv.mkFunctionSort(uSort2, slv.getIntegerSort());
+    Term b12 = slv.mkVar(bvSort2, "b1");
+    Term b112 = slv.mkVar(bvSort2, "b1");
+    Term b42 = slv.mkVar(uSort2, "b4");
+    Term v12 = slv.mkConst(bvSort2, "v1");
+    Term v22 = slv.mkConst(slv.getIntegerSort(), "v2");
+    Term f12 = slv.mkConst(funSort12, "f1");
+    Term f22 = slv.mkConst(funSort22, "f2");
+    assertDoesNotThrow(
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f1, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f2}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f22}, new Term[][] {{b1, b112}, {b42}}, new Term[] {v12, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f22}, new Term[][] {{b12, b11}, {b42}}, new Term[] {v12, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b4}}, new Term[] {v12, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v1, v22}));
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> slv.defineFunsRec(
+                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v2}));
+  }
+
+  @Test void defineFunsRecWrongLogic() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_BV");
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
+    Sort funSort2 = d_solver.mkFunctionSort(uSort, d_solver.getIntegerSort());
+    Term b = d_solver.mkVar(bvSort, "b");
+    Term u = d_solver.mkVar(uSort, "u");
+    Term v1 = d_solver.mkConst(bvSort, "v1");
+    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
+    Term f1 = d_solver.mkConst(funSort1, "f1");
+    Term f2 = d_solver.mkConst(funSort2, "f2");
+    assertThrows(CVC5ApiException.class,
+        ()
+            -> d_solver.defineFunsRec(
+                new Term[] {f1, f2}, new Term[][] {{b, b}, {u}}, new Term[] {v1, v2}));
+  }
+
+  @Test void defineFunsRecGlobal() throws CVC5ApiException
+  {
+    Sort bSort = d_solver.getBooleanSort();
+    Sort fSort = d_solver.mkFunctionSort(bSort, bSort);
+
+    d_solver.push();
+    Term bTrue = d_solver.mkBoolean(true);
+    Term b = d_solver.mkVar(bSort, "b");
+    Term gSym = d_solver.mkConst(fSort, "g");
+    // (define-funs-rec ((g ((b Bool)) Bool)) (b))
+    d_solver.defineFunsRec(new Term[] {gSym}, new Term[][] {{b}}, new Term[] {b}, true);
+
+    // (assert (not (g true)))
+    d_solver.assertFormula(d_solver.mkTerm(APPLY_UF, gSym, bTrue).notTerm());
+    assertTrue(d_solver.checkSat().isUnsat());
+    d_solver.pop();
+    // (assert (not (g true)))
+    d_solver.assertFormula(d_solver.mkTerm(APPLY_UF, gSym, bTrue).notTerm());
+    assertTrue(d_solver.checkSat().isUnsat());
+  }
+
+  @Test void uFIteration()
+  {
+    Sort intSort = d_solver.getIntegerSort();
+    Sort funSort = d_solver.mkFunctionSort(new Sort[] {intSort, intSort}, intSort);
+    Term x = d_solver.mkConst(intSort, "x");
+    Term y = d_solver.mkConst(intSort, "y");
+    Term f = d_solver.mkConst(funSort, "f");
+    Term fxy = d_solver.mkTerm(APPLY_UF, f, x, y);
+
+    // Expecting the uninterpreted function to be one of the children
+    Term expected_children[] = new Term[] {f, x, y};
+    int idx = 0;
+    for (Term c : fxy)
+    {
+      assertEquals(c, expected_children[idx]);
+      idx++;
+    }
+  }
+
+  @Test void getInfo()
+  {
+    assertDoesNotThrow(() -> d_solver.getInfo("name"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.getInfo("asdf"));
+  }
+
+  @Test void getInterpolant() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_LIA");
+    d_solver.setOption("produce-interpols", "default");
+    d_solver.setOption("incremental", "false");
+
+    Sort intSort = d_solver.getIntegerSort();
+    Term zero = d_solver.mkInteger(0);
+    Term x = d_solver.mkConst(intSort, "x");
+    Term y = d_solver.mkConst(intSort, "y");
+    Term z = d_solver.mkConst(intSort, "z");
+
+    // Assumptions for interpolation: x + y > 0 /\ x < 0
+    d_solver.assertFormula(d_solver.mkTerm(GT, d_solver.mkTerm(PLUS, x, y), zero));
+    d_solver.assertFormula(d_solver.mkTerm(LT, x, zero));
+    // Conjecture for interpolation: y + z > 0 \/ z < 0
+    Term conj = d_solver.mkTerm(
+        OR, d_solver.mkTerm(GT, d_solver.mkTerm(PLUS, y, z), zero), d_solver.mkTerm(LT, z, zero));
+    Term output = d_solver.getNullTerm();
+    // Call the interpolation api, while the resulting interpolant is the output
+    d_solver.getInterpolant(conj, output);
+
+    // We expect the resulting output to be a boolean formula
+    assertTrue(output.getSort().isBoolean());
+  }
+
+  @Test void getOp() throws CVC5ApiException
+  {
+    Sort bv32 = d_solver.mkBitVectorSort(32);
+    Term a = d_solver.mkConst(bv32, "a");
+    Op ext = d_solver.mkOp(BITVECTOR_EXTRACT, 2, 1);
+    Term exta = d_solver.mkTerm(ext, a);
+
+    assertFalse(a.hasOp());
+    assertThrows(CVC5ApiException.class, () -> a.getOp());
+    assertTrue(exta.hasOp());
+    assertEquals(exta.getOp(), ext);
+
+    // Test Datatypes -- more complicated
+    DatatypeDecl consListSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    cons.addSelectorSelf("tail");
+    consListSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    consListSpec.addConstructor(nil);
+    Sort consListSort = d_solver.mkDatatypeSort(consListSpec);
+    Datatype consList = consListSort.getDatatype();
+
+    Term consTerm = consList.getConstructorTerm("cons");
+    Term nilTerm = consList.getConstructorTerm("nil");
+    Term headTerm = consList.getConstructor("cons").getSelectorTerm("head");
+
+    Term listnil = d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm);
+    Term listcons1 = d_solver.mkTerm(APPLY_CONSTRUCTOR, consTerm, d_solver.mkInteger(1), listnil);
+    Term listhead = d_solver.mkTerm(APPLY_SELECTOR, headTerm, listcons1);
+
+    assertTrue(listnil.hasOp());
+    assertTrue(listcons1.hasOp());
+    assertTrue(listhead.hasOp());
+  }
+
+  @Test void getOption()
+  {
+    assertDoesNotThrow(() -> d_solver.getOption("incremental"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.getOption("asdf"));
+  }
+
+  @Test void getOptionNames()
+  {
+    String[] names = d_solver.getOptionNames();
+    assertTrue(names.length > 100);
+    assertTrue(Arrays.asList(names).contains("verbose"));
+    assertFalse(Arrays.asList(names).contains("foobar"));
+  }
+
+  @Test void getOptionInfo()
+  {
+    List<Executable> assertions = new ArrayList<>();
+    {
+      assertions.add(
+          () -> assertThrows(CVC5ApiException.class, () -> d_solver.getOptionInfo("asdf-invalid")));
+    }
+    {
+      OptionInfo info = d_solver.getOptionInfo("verbose");
+      assertions.add(() -> assertEquals("verbose", info.getName()));
+      assertions.add(
+          () -> assertEquals(Arrays.asList(new String[] {}), Arrays.asList(info.getAliases())));
+      assertions.add(() -> assertTrue(info.getBaseInfo() instanceof OptionInfo.VoidInfo));
+    }
+    {
+      // int64 type with default
+      OptionInfo info = d_solver.getOptionInfo("verbosity");
+      assertions.add(() -> assertEquals("verbosity", info.getName()));
+      assertions.add(
+          () -> assertEquals(Arrays.asList(new String[] {}), Arrays.asList(info.getAliases())));
+      assertions.add(
+          () -> assertTrue(info.getBaseInfo().getClass() == OptionInfo.NumberInfo.class));
+      OptionInfo.NumberInfo<BigInteger> numInfo =
+          (OptionInfo.NumberInfo<BigInteger>) info.getBaseInfo();
+      assertions.add(() -> assertEquals(0, numInfo.getDefaultValue().intValue()));
+      assertions.add(() -> assertEquals(0, numInfo.getCurrentValue().intValue()));
+      assertions.add(
+          () -> assertFalse(numInfo.getMinimum() != null || numInfo.getMaximum() != null));
+      assertions.add(() -> assertEquals(info.intValue().intValue(), 0));
+    }
+    assertAll(assertions);
+    {
+      OptionInfo info = d_solver.getOptionInfo("random-freq");
+      assertEquals(info.getName(), "random-freq");
+      assertEquals(
+          Arrays.asList(info.getAliases()), Arrays.asList(new String[] {"random-frequency"}));
+      assertTrue(info.getBaseInfo().getClass() == OptionInfo.NumberInfo.class);
+      OptionInfo.NumberInfo<Double> ni = (OptionInfo.NumberInfo<Double>) info.getBaseInfo();
+      assertEquals(ni.getCurrentValue(), 0.0);
+      assertEquals(ni.getDefaultValue(), 0.0);
+      assertTrue(ni.getMinimum() != null && ni.getMaximum() != null);
+      assertEquals(ni.getMinimum(), 0.0);
+      assertEquals(ni.getMaximum(), 1.0);
+      assertEquals(info.doubleValue(), 0.0);
+    }
+    {
+      // mode option
+      OptionInfo info = d_solver.getOptionInfo("output");
+      assertions.clear();
+      assertions.add(() -> assertEquals("output", info.getName()));
+      assertions.add(
+          () -> assertEquals(Arrays.asList(new String[] {}), Arrays.asList(info.getAliases())));
+      assertions.add(() -> assertTrue(info.getBaseInfo().getClass() == OptionInfo.ModeInfo.class));
+      OptionInfo.ModeInfo modeInfo = (OptionInfo.ModeInfo) info.getBaseInfo();
+      assertions.add(() -> assertEquals("NONE", modeInfo.getDefaultValue()));
+      assertions.add(() -> assertEquals("OutputTag::NONE", modeInfo.getCurrentValue()));
+      assertions.add(() -> assertTrue(Arrays.asList(modeInfo.getModes()).contains("NONE")));
+    }
+    assertAll(assertions);
+  }
+
+  @Test void getUnsatAssumptions1()
+  {
+    d_solver.setOption("incremental", "false");
+    d_solver.checkSatAssuming(d_solver.mkFalse());
+    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatAssumptions());
+  }
+
+  @Test void getUnsatAssumptions2()
+  {
+    d_solver.setOption("incremental", "true");
+    d_solver.setOption("produce-unsat-assumptions", "false");
+    d_solver.checkSatAssuming(d_solver.mkFalse());
+    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatAssumptions());
+  }
+
+  @Test void getUnsatAssumptions3()
+  {
+    d_solver.setOption("incremental", "true");
+    d_solver.setOption("produce-unsat-assumptions", "true");
+    d_solver.checkSatAssuming(d_solver.mkFalse());
+    assertDoesNotThrow(() -> d_solver.getUnsatAssumptions());
+    d_solver.checkSatAssuming(d_solver.mkTrue());
+    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatAssumptions());
+  }
+
+  @Test void getUnsatCore1()
+  {
+    d_solver.setOption("incremental", "false");
+    d_solver.assertFormula(d_solver.mkFalse());
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatCore());
+  }
+
+  @Test void getUnsatCore2()
+  {
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-unsat-cores", "false");
+    d_solver.assertFormula(d_solver.mkFalse());
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatCore());
+  }
+
+  @Test void getUnsatCoreAndProof()
+  {
+    d_solver.setOption("incremental", "true");
+    d_solver.setOption("produce-unsat-cores", "true");
+    d_solver.setOption("produce-proofs", "true");
+
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
+    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    Term f = d_solver.mkConst(uToIntSort, "f");
+    Term p = d_solver.mkConst(intPredSort, "p");
+    Term zero = d_solver.mkInteger(0);
+    Term one = d_solver.mkInteger(1);
+    Term f_x = d_solver.mkTerm(Kind.APPLY_UF, f, x);
+    Term f_y = d_solver.mkTerm(Kind.APPLY_UF, f, y);
+    Term sum = d_solver.mkTerm(Kind.PLUS, f_x, f_y);
+    Term p_0 = d_solver.mkTerm(Kind.APPLY_UF, p, zero);
+    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
+    d_solver.assertFormula(d_solver.mkTerm(Kind.GT, zero, f_x));
+    d_solver.assertFormula(d_solver.mkTerm(Kind.GT, zero, f_y));
+    d_solver.assertFormula(d_solver.mkTerm(Kind.GT, sum, one));
+    d_solver.assertFormula(p_0);
+    d_solver.assertFormula(p_f_y.notTerm());
+    assertTrue(d_solver.checkSat().isUnsat());
+
+    Term[] unsat_core = d_solver.getUnsatCore();
+
+    assertDoesNotThrow(() -> d_solver.getProof());
+
+    d_solver.resetAssertions();
+    for (Term t : unsat_core)
+    {
+      d_solver.assertFormula(t);
+    }
+    Result res = d_solver.checkSat();
+    assertTrue(res.isUnsat());
+    assertDoesNotThrow(() -> d_solver.getProof());
+  }
+
+  @Test void getDifficulty()
+  {
+    d_solver.setOption("produce-difficulty", "true");
+    // cannot ask before a check sat
+    assertThrows(CVC5ApiException.class, () -> d_solver.getDifficulty());
+    d_solver.checkSat();
+    assertDoesNotThrow(() -> d_solver.getDifficulty());
+  }
+
+  @Test void getDifficulty2()
+  {
+    d_solver.checkSat();
+    // option is not set
+    assertThrows(CVC5ApiException.class, () -> d_solver.getDifficulty());
+  }
+
+  @Test void getDifficulty3() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-difficulty", "true");
+    Sort intSort = d_solver.getIntegerSort();
+    Term x = d_solver.mkConst(intSort, "x");
+    Term zero = d_solver.mkInteger(0);
+    Term ten = d_solver.mkInteger(10);
+    Term f0 = d_solver.mkTerm(GEQ, x, ten);
+    Term f1 = d_solver.mkTerm(GEQ, zero, x);
+    d_solver.checkSat();
+    Map<Term, Term> dmap = d_solver.getDifficulty();
+    // difficulty should map assertions to integer values
+    for (Map.Entry<Term, Term> t : dmap.entrySet())
+    {
+      assertTrue(t.getKey() == f0 || t.getKey() == f1);
+      assertTrue(t.getValue().getKind() == Kind.CONST_RATIONAL);
+    }
+  }
+
+  @Test void getValue1()
+  {
+    d_solver.setOption("produce-models", "false");
+    Term t = d_solver.mkTrue();
+    d_solver.assertFormula(t);
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getValue(t));
+  }
+
+  @Test void getValue2()
+  {
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkFalse();
+    d_solver.assertFormula(t);
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getValue(t));
+  }
+
+  @Test void getValue3()
+  {
+    d_solver.setOption("produce-models", "true");
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
+    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
+    Term[] unsat_core;
+
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    Term z = d_solver.mkConst(uSort, "z");
+    Term f = d_solver.mkConst(uToIntSort, "f");
+    Term p = d_solver.mkConst(intPredSort, "p");
+    Term zero = d_solver.mkInteger(0);
+    Term one = d_solver.mkInteger(1);
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
+
+    d_solver.assertFormula(d_solver.mkTerm(LEQ, zero, f_x));
+    d_solver.assertFormula(d_solver.mkTerm(LEQ, zero, f_y));
+    d_solver.assertFormula(d_solver.mkTerm(LEQ, sum, one));
+    d_solver.assertFormula(p_0.notTerm());
+    d_solver.assertFormula(p_f_y);
+    assertTrue(d_solver.checkSat().isSat());
+    assertDoesNotThrow(() -> d_solver.getValue(x));
+    assertDoesNotThrow(() -> d_solver.getValue(y));
+    assertDoesNotThrow(() -> d_solver.getValue(z));
+    assertDoesNotThrow(() -> d_solver.getValue(sum));
+    assertDoesNotThrow(() -> d_solver.getValue(p_f_y));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.getValue(x));
+  }
+
+  @Test void getModelDomainElements()
+  {
+    d_solver.setOption("produce-models", "true");
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort intSort = d_solver.getIntegerSort();
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    Term z = d_solver.mkConst(uSort, "z");
+    Term f = d_solver.mkTerm(DISTINCT, x, y, z);
+    d_solver.assertFormula(f);
+    d_solver.checkSat();
+    assertDoesNotThrow(() -> d_solver.getModelDomainElements(uSort));
+    assertTrue(d_solver.getModelDomainElements(uSort).length >= 3);
+    assertThrows(CVC5ApiException.class, () -> d_solver.getModelDomainElements(intSort));
+  }
+
+  @Test void getModelDomainElements2()
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("finite-model-find", "true");
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkVar(uSort, "x");
+    Term y = d_solver.mkVar(uSort, "y");
+    Term eq = d_solver.mkTerm(EQUAL, x, y);
+    Term bvl = d_solver.mkTerm(BOUND_VAR_LIST, x, y);
+    Term f = d_solver.mkTerm(FORALL, bvl, eq);
+    d_solver.assertFormula(f);
+    d_solver.checkSat();
+    assertDoesNotThrow(() -> d_solver.getModelDomainElements(uSort));
+    // a model for the above must interpret u as size 1
+    assertTrue(d_solver.getModelDomainElements(uSort).length == 1);
+  }
+
+  @Test void isModelCoreSymbol()
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("model-cores", "simple");
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    Term z = d_solver.mkConst(uSort, "z");
+    Term zero = d_solver.mkInteger(0);
+    Term f = d_solver.mkTerm(NOT, d_solver.mkTerm(EQUAL, x, y));
+    d_solver.assertFormula(f);
+    d_solver.checkSat();
+    assertTrue(d_solver.isModelCoreSymbol(x));
+    assertTrue(d_solver.isModelCoreSymbol(y));
+    assertFalse(d_solver.isModelCoreSymbol(z));
+    assertThrows(CVC5ApiException.class, () -> d_solver.isModelCoreSymbol(zero));
+  }
+
+  @Test void getModel()
+  {
+    d_solver.setOption("produce-models", "true");
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    Term z = d_solver.mkConst(uSort, "z");
+    Term f = d_solver.mkTerm(NOT, d_solver.mkTerm(EQUAL, x, y));
+    d_solver.assertFormula(f);
+    d_solver.checkSat();
+    Sort[] sorts = new Sort[] {uSort};
+    Term[] terms = new Term[] {x, y};
+    assertDoesNotThrow(() -> d_solver.getModel(sorts, terms));
+    Term nullTerm = d_solver.getNullTerm();
+    Term[] terms2 = new Term[] {x, y, nullTerm};
+    assertThrows(CVC5ApiException.class, () -> d_solver.getModel(sorts, terms2));
+  }
+
+  @Test void getModel2()
+  {
+    d_solver.setOption("produce-models", "true");
+    Sort[] sorts = new Sort[] {};
+    Term[] terms = new Term[] {};
+    assertThrows(CVC5ApiException.class, () -> d_solver.getModel(sorts, terms));
+  }
+
+  @Test void getModel3()
+  {
+    d_solver.setOption("produce-models", "true");
+    Sort[] sorts = new Sort[] {};
+    final Term[] terms = new Term[] {};
+    d_solver.checkSat();
+    assertDoesNotThrow(() -> d_solver.getModel(sorts, terms));
+    Sort integer = d_solver.getIntegerSort();
+    Sort[] sorts2 = new Sort[] {integer};
+    assertThrows(CVC5ApiException.class, () -> d_solver.getModel(sorts2, terms));
+  }
+
+  @Test void getQuantifierElimination()
+  {
+    Term x = d_solver.mkVar(d_solver.getBooleanSort(), "x");
+    Term forall = d_solver.mkTerm(FORALL,
+        d_solver.mkTerm(BOUND_VAR_LIST, x),
+        d_solver.mkTerm(OR, x, d_solver.mkTerm(NOT, x)));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.getQuantifierElimination(d_solver.getNullTerm()));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.getQuantifierElimination(new Solver().mkBoolean(false)));
+
+    assertDoesNotThrow(() -> d_solver.getQuantifierElimination(forall));
+  }
+
+  @Test void getQuantifierEliminationDisjunct()
+  {
+    Term x = d_solver.mkVar(d_solver.getBooleanSort(), "x");
+    Term forall = d_solver.mkTerm(FORALL,
+        d_solver.mkTerm(BOUND_VAR_LIST, x),
+        d_solver.mkTerm(OR, x, d_solver.mkTerm(NOT, x)));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.getQuantifierEliminationDisjunct(d_solver.getNullTerm()));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.getQuantifierEliminationDisjunct(new Solver().mkBoolean(false)));
+
+    assertDoesNotThrow(() -> d_solver.getQuantifierEliminationDisjunct(forall));
+  }
+
+  @Test void declareSeparationHeap() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    Sort integer = d_solver.getIntegerSort();
+    assertDoesNotThrow(() -> d_solver.declareSeparationHeap(integer, integer));
+    // cannot declare separation logic heap more than once
+    assertThrows(CVC5ApiException.class, () -> d_solver.declareSeparationHeap(integer, integer));
+  }
+
+  /**
+   * Helper function for testGetSeparation{Heap,Nil}TermX. Asserts and checks
+   * some simple separation logic constraints.
+   */
+
+  void checkSimpleSeparationConstraints(Solver solver)
+  {
+    Sort integer = solver.getIntegerSort();
+    // declare the separation heap
+    solver.declareSeparationHeap(integer, integer);
+    Term x = solver.mkConst(integer, "x");
+    Term p = solver.mkConst(integer, "p");
+    Term heap = solver.mkTerm(SEP_PTO, p, x);
+    solver.assertFormula(heap);
+    Term nil = solver.mkSepNil(integer);
+    solver.assertFormula(nil.eqTerm(solver.mkReal(5)));
+    solver.checkSat();
+  }
+
+  @Test void getSeparationHeapTerm1() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_BV");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkTrue();
+    d_solver.assertFormula(t);
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
+  }
+
+  @Test void getSeparationHeapTerm2() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "false");
+    checkSimpleSeparationConstraints(d_solver);
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
+  }
+
+  @Test void getSeparationHeapTerm3() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkFalse();
+    d_solver.assertFormula(t);
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
+  }
+
+  @Test void getSeparationHeapTerm4() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkTrue();
+    d_solver.assertFormula(t);
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
+  }
+
+  @Test void getSeparationHeapTerm5() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    checkSimpleSeparationConstraints(d_solver);
+    assertDoesNotThrow(() -> d_solver.getSeparationHeap());
+  }
+
+  @Test void getSeparationNilTerm1() throws CVC5ApiException
+  {
+    d_solver.setLogic("QF_BV");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkTrue();
+    d_solver.assertFormula(t);
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
+  }
+
+  @Test void getSeparationNilTerm2() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "false");
+    checkSimpleSeparationConstraints(d_solver);
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
+  }
+
+  @Test void getSeparationNilTerm3() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkFalse();
+    d_solver.assertFormula(t);
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
+  }
+
+  @Test void getSeparationNilTerm4() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    Term t = d_solver.mkTrue();
+    d_solver.assertFormula(t);
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
+  }
+
+  @Test void getSeparationNilTerm5() throws CVC5ApiException
+  {
+    d_solver.setLogic("ALL");
+    d_solver.setOption("incremental", "false");
+    d_solver.setOption("produce-models", "true");
+    checkSimpleSeparationConstraints(d_solver);
+    assertDoesNotThrow(() -> d_solver.getSeparationNilTerm());
+  }
+
+  @Test void push1()
+  {
+    d_solver.setOption("incremental", "true");
+    assertDoesNotThrow(() -> d_solver.push(1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("incremental", "false"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("incremental", "true"));
+  }
+
+  @Test void push2()
+  {
+    d_solver.setOption("incremental", "false");
+    assertThrows(CVC5ApiException.class, () -> d_solver.push(1));
+  }
+
+  @Test void pop1()
+  {
+    d_solver.setOption("incremental", "false");
+    assertThrows(CVC5ApiException.class, () -> d_solver.pop(1));
+  }
+
+  @Test void pop2()
+  {
+    d_solver.setOption("incremental", "true");
+    assertThrows(CVC5ApiException.class, () -> d_solver.pop(1));
+  }
+
+  @Test void pop3()
+  {
+    d_solver.setOption("incremental", "true");
+    assertDoesNotThrow(() -> d_solver.push(1));
+    assertDoesNotThrow(() -> d_solver.pop(1));
+    assertThrows(CVC5ApiException.class, () -> d_solver.pop(1));
+  }
+
+  @Test void blockModel1()
+  {
+    d_solver.setOption("produce-models", "true");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModel());
+  }
+
+  @Test void blockModel2() throws CVC5ApiException
+  {
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModel());
+  }
+
+  @Test void blockModel3() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModel());
+  }
+
+  @Test void blockModel4() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertDoesNotThrow(() -> d_solver.blockModel());
+  }
+
+  @Test void blockModelValues1() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {}));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.blockModelValues(new Term[] {d_solver.getNullTerm()}));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.blockModelValues(new Term[] {new Solver().mkBoolean(false)}));
+  }
+
+  @Test void blockModelValues2() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {x}));
+  }
+
+  @Test void blockModelValues3() throws CVC5ApiException
+  {
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {x}));
+  }
+
+  @Test void blockModelValues4() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {x}));
+  }
+
+  @Test void blockModelValues5() throws CVC5ApiException
+  {
+    d_solver.setOption("produce-models", "true");
+    d_solver.setOption("block-models", "literals");
+    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
+    d_solver.assertFormula(x.eqTerm(x));
+    d_solver.checkSat();
+    assertDoesNotThrow(() -> d_solver.blockModelValues(new Term[] {x}));
+  }
+
+  @Test void setInfo() throws CVC5ApiException
+  {
+    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("cvc4-lagic", "QF_BV"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("cvc2-logic", "QF_BV"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("cvc4-logic", "asdf"));
+
+    assertDoesNotThrow(() -> d_solver.setInfo("source", "asdf"));
+    assertDoesNotThrow(() -> d_solver.setInfo("category", "asdf"));
+    assertDoesNotThrow(() -> d_solver.setInfo("difficulty", "asdf"));
+    assertDoesNotThrow(() -> d_solver.setInfo("filename", "asdf"));
+    assertDoesNotThrow(() -> d_solver.setInfo("license", "asdf"));
+    assertDoesNotThrow(() -> d_solver.setInfo("name", "asdf"));
+    assertDoesNotThrow(() -> d_solver.setInfo("notes", "asdf"));
+
+    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2"));
+    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2.0"));
+    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2.5"));
+    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2.6"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("smt-lib-version", ".0"));
+
+    assertDoesNotThrow(() -> d_solver.setInfo("status", "sat"));
+    assertDoesNotThrow(() -> d_solver.setInfo("status", "unsat"));
+    assertDoesNotThrow(() -> d_solver.setInfo("status", "unknown"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("status", "asdf"));
+  }
+
+  @Test void simplify() throws CVC5ApiException
+  {
+    assertThrows(CVC5ApiException.class, () -> d_solver.simplify(d_solver.getNullTerm()));
+
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
+    Sort funSort2 = d_solver.mkFunctionSort(uSort, d_solver.getIntegerSort());
+    DatatypeDecl consListSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    cons.addSelectorSelf("tail");
+    consListSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    consListSpec.addConstructor(nil);
+    Sort consListSort = d_solver.mkDatatypeSort(consListSpec);
+
+    Term x = d_solver.mkConst(bvSort, "x");
+    assertDoesNotThrow(() -> d_solver.simplify(x));
+    Term a = d_solver.mkConst(bvSort, "a");
+    assertDoesNotThrow(() -> d_solver.simplify(a));
+    Term b = d_solver.mkConst(bvSort, "b");
+    assertDoesNotThrow(() -> d_solver.simplify(b));
+    Term x_eq_x = d_solver.mkTerm(EQUAL, x, x);
+    assertDoesNotThrow(() -> d_solver.simplify(x_eq_x));
+    assertNotEquals(d_solver.mkTrue(), x_eq_x);
+    assertEquals(d_solver.mkTrue(), d_solver.simplify(x_eq_x));
+    Term x_eq_b = d_solver.mkTerm(EQUAL, x, b);
+    assertDoesNotThrow(() -> d_solver.simplify(x_eq_b));
+    assertNotEquals(d_solver.mkTrue(), x_eq_b);
+    assertNotEquals(d_solver.mkTrue(), d_solver.simplify(x_eq_b));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.simplify(x));
+
+    Term i1 = d_solver.mkConst(d_solver.getIntegerSort(), "i1");
+    assertDoesNotThrow(() -> d_solver.simplify(i1));
+    Term i2 = d_solver.mkTerm(MULT, i1, d_solver.mkInteger("23"));
+    assertDoesNotThrow(() -> d_solver.simplify(i2));
+    assertNotEquals(i1, i2);
+    assertNotEquals(i1, d_solver.simplify(i2));
+    Term i3 = d_solver.mkTerm(PLUS, i1, d_solver.mkInteger(0));
+    assertDoesNotThrow(() -> d_solver.simplify(i3));
+    assertNotEquals(i1, i3);
+    assertEquals(i1, d_solver.simplify(i3));
+
+    Datatype consList = consListSort.getDatatype();
+    Term dt1 = d_solver.mkTerm(APPLY_CONSTRUCTOR,
+        consList.getConstructorTerm("cons"),
+        d_solver.mkInteger(0),
+        d_solver.mkTerm(APPLY_CONSTRUCTOR, consList.getConstructorTerm("nil")));
+    assertDoesNotThrow(() -> d_solver.simplify(dt1));
+    Term dt2 = d_solver.mkTerm(
+        APPLY_SELECTOR, consList.getConstructor("cons").getSelectorTerm("head"), dt1);
+    assertDoesNotThrow(() -> d_solver.simplify(dt2));
+
+    Term b1 = d_solver.mkVar(bvSort, "b1");
+    assertDoesNotThrow(() -> d_solver.simplify(b1));
+    Term b2 = d_solver.mkVar(bvSort, "b1");
+    assertDoesNotThrow(() -> d_solver.simplify(b2));
+    Term b3 = d_solver.mkVar(uSort, "b3");
+    assertDoesNotThrow(() -> d_solver.simplify(b3));
+    Term v1 = d_solver.mkConst(bvSort, "v1");
+    assertDoesNotThrow(() -> d_solver.simplify(v1));
+    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
+    assertDoesNotThrow(() -> d_solver.simplify(v2));
+    Term f1 = d_solver.mkConst(funSort1, "f1");
+    assertDoesNotThrow(() -> d_solver.simplify(f1));
+    Term f2 = d_solver.mkConst(funSort2, "f2");
+    assertDoesNotThrow(() -> d_solver.simplify(f2));
+    d_solver.defineFunsRec(new Term[] {f1, f2}, new Term[][] {{b1, b2}, {b3}}, new Term[] {v1, v2});
+    assertDoesNotThrow(() -> d_solver.simplify(f1));
+    assertDoesNotThrow(() -> d_solver.simplify(f2));
+  }
+
+  @Test void assertFormula()
+  {
+    assertDoesNotThrow(() -> d_solver.assertFormula(d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.assertFormula(d_solver.getNullTerm()));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.assertFormula(d_solver.mkTrue()));
+  }
+
+  @Test void checkEntailed()
+  {
+    d_solver.setOption("incremental", "false");
+    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkEntailed(d_solver.mkTrue()));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.checkEntailed(d_solver.mkTrue()));
+  }
+
+  @Test void checkEntailed1()
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Term x = d_solver.mkConst(boolSort, "x");
+    Term y = d_solver.mkConst(boolSort, "y");
+    Term z = d_solver.mkTerm(AND, x, y);
+    d_solver.setOption("incremental", "true");
+    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkEntailed(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
+    assertDoesNotThrow(() -> d_solver.checkEntailed(z));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.checkEntailed(d_solver.mkTrue()));
+  }
+
+  @Test void checkEntailed2()
+  {
+    d_solver.setOption("incremental", "true");
+
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
+    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term n = d_solver.getNullTerm();
+    // Constants
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    // Functions
+    Term f = d_solver.mkConst(uToIntSort, "f");
+    Term p = d_solver.mkConst(intPredSort, "p");
+    // Values
+    Term zero = d_solver.mkInteger(0);
+    Term one = d_solver.mkInteger(1);
+    // Terms
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
+    // Assertions
+    Term assertions = d_solver.mkTerm(AND,
+        new Term[] {
+            d_solver.mkTerm(LEQ, zero, f_x), // 0 <= f(x)
+            d_solver.mkTerm(LEQ, zero, f_y), // 0 <= f(y)
+            d_solver.mkTerm(LEQ, sum, one), // f(x) + f(y) <= 1
+            p_0.notTerm(), // not p(0)
+            p_f_y // p(f(y))
+        });
+
+    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
+    d_solver.assertFormula(assertions);
+    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTerm(DISTINCT, x, y)));
+    assertDoesNotThrow(()
+                           -> d_solver.checkEntailed(
+                               new Term[] {d_solver.mkFalse(), d_solver.mkTerm(DISTINCT, x, y)}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkEntailed(n));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.checkEntailed(new Term[] {n, d_solver.mkTerm(DISTINCT, x, y)}));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.checkEntailed(d_solver.mkTrue()));
+  }
+
+  @Test void checkSat() throws CVC5ApiException
+  {
+    d_solver.setOption("incremental", "false");
+    assertDoesNotThrow(() -> d_solver.checkSat());
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkSat());
+  }
+
+  @Test void checkSatAssuming() throws CVC5ApiException
+  {
+    d_solver.setOption("incremental", "false");
+    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkSatAssuming(d_solver.mkTrue()));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.checkSatAssuming(d_solver.mkTrue()));
+  }
+
+  @Test void checkSatAssuming1() throws CVC5ApiException
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Term x = d_solver.mkConst(boolSort, "x");
+    Term y = d_solver.mkConst(boolSort, "y");
+    Term z = d_solver.mkTerm(AND, x, y);
+    d_solver.setOption("incremental", "true");
+    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkSatAssuming(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
+    assertDoesNotThrow(() -> d_solver.checkSatAssuming(z));
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.checkSatAssuming(d_solver.mkTrue()));
+  }
+
+  @Test void checkSatAssuming2() throws CVC5ApiException
+  {
+    d_solver.setOption("incremental", "true");
+
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
+    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term n = d_solver.getNullTerm();
+    // Constants
+    Term x = d_solver.mkConst(uSort, "x");
+    Term y = d_solver.mkConst(uSort, "y");
+    // Functions
+    Term f = d_solver.mkConst(uToIntSort, "f");
+    Term p = d_solver.mkConst(intPredSort, "p");
+    // Values
+    Term zero = d_solver.mkInteger(0);
+    Term one = d_solver.mkInteger(1);
+    // Terms
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
+    // Assertions
+    Term assertions = d_solver.mkTerm(AND,
+        new Term[] {
+            d_solver.mkTerm(LEQ, zero, f_x), // 0 <= f(x)
+            d_solver.mkTerm(LEQ, zero, f_y), // 0 <= f(y)
+            d_solver.mkTerm(LEQ, sum, one), // f(x) + f(y) <= 1
+            p_0.notTerm(), // not p(0)
+            p_f_y // p(f(y))
+        });
+
+    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
+    d_solver.assertFormula(assertions);
+    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTerm(DISTINCT, x, y)));
+    assertDoesNotThrow(()
+                           -> d_solver.checkSatAssuming(
+                               new Term[] {d_solver.mkFalse(), d_solver.mkTerm(DISTINCT, x, y)}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.checkSatAssuming(n));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.checkSatAssuming(new Term[] {n, d_solver.mkTerm(DISTINCT, x, y)}));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.checkSatAssuming(d_solver.mkTrue()));
+  }
+
+  @Test void setLogic() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.setLogic("AUFLIRA"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setLogic("AF_BV"));
+    d_solver.assertFormula(d_solver.mkTrue());
+    assertThrows(CVC5ApiException.class, () -> d_solver.setLogic("AUFLIRA"));
+  }
+
+  @Test void setOption() throws CVC5ApiException
+  {
+    assertDoesNotThrow(() -> d_solver.setOption("bv-sat-solver", "minisat"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("bv-sat-solver", "1"));
+    d_solver.assertFormula(d_solver.mkTrue());
+    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("bv-sat-solver", "minisat"));
+  }
+
+  @Test void resetAssertions() throws CVC5ApiException
+  {
+    d_solver.setOption("incremental", "true");
+
+    Sort bvSort = d_solver.mkBitVectorSort(4);
+    Term one = d_solver.mkBitVector(4, 1);
+    Term x = d_solver.mkConst(bvSort, "x");
+    Term ule = d_solver.mkTerm(BITVECTOR_ULE, x, one);
+    Term srem = d_solver.mkTerm(BITVECTOR_SREM, one, x);
+    d_solver.push(4);
+    Term slt = d_solver.mkTerm(BITVECTOR_SLT, srem, one);
+    d_solver.resetAssertions();
+    d_solver.checkSatAssuming(new Term[] {slt, ule});
+  }
+
+  @Test void mkSygusVar() throws CVC5ApiException
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort intSort = d_solver.getIntegerSort();
+    Sort funSort = d_solver.mkFunctionSort(intSort, boolSort);
+
+    assertDoesNotThrow(() -> d_solver.mkSygusVar(boolSort));
+    assertDoesNotThrow(() -> d_solver.mkSygusVar(funSort));
+    assertDoesNotThrow(() -> d_solver.mkSygusVar(boolSort, ("b")));
+    assertDoesNotThrow(() -> d_solver.mkSygusVar(funSort, ""));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkSygusVar(d_solver.getNullSort()));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkSygusVar(d_solver.getNullSort(), "a"));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.mkSygusVar(boolSort));
+  }
+
+  @Test void mkSygusGrammar() throws CVC5ApiException
+  {
+    Term nullTerm = d_solver.getNullTerm();
+    Term boolTerm = d_solver.mkBoolean(true);
+    Term boolVar = d_solver.mkVar(d_solver.getBooleanSort());
+    Term intVar = d_solver.mkVar(d_solver.getIntegerSort());
+
+    assertDoesNotThrow(() -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {intVar}));
+    assertDoesNotThrow(() -> d_solver.mkSygusGrammar(new Term[] {boolVar}, new Term[] {intVar}));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {}));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {nullTerm}));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {boolTerm}));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkSygusGrammar(new Term[] {boolTerm}, new Term[] {intVar}));
+
+    Solver slv = new Solver();
+    Term boolVar2 = slv.mkVar(slv.getBooleanSort());
+    Term intVar2 = slv.mkVar(slv.getIntegerSort());
+    assertDoesNotThrow(() -> slv.mkSygusGrammar(new Term[] {boolVar2}, new Term[] {intVar2}));
+
+    assertThrows(CVC5ApiException.class,
+        () -> slv.mkSygusGrammar(new Term[] {boolVar}, new Term[] {intVar2}));
+    assertThrows(CVC5ApiException.class,
+        () -> slv.mkSygusGrammar(new Term[] {boolVar2}, new Term[] {intVar}));
+  }
+
+  @Test void synthFun() throws CVC5ApiException
+  {
+    Sort nullSort = d_solver.getNullSort();
+    Sort bool = d_solver.getBooleanSort();
+    Sort integer = d_solver.getIntegerSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term x = d_solver.mkVar(bool);
+
+    Term start1 = d_solver.mkVar(bool);
+    Term start2 = d_solver.mkVar(integer);
+
+    Grammar g1 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start1});
+    g1.addRule(start1, d_solver.mkBoolean(false));
+
+    Grammar g2 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start2});
+    g2.addRule(start2, d_solver.mkInteger(0));
+
+    assertDoesNotThrow(() -> d_solver.synthFun("", new Term[] {}, bool));
+    assertDoesNotThrow(() -> d_solver.synthFun("f1", new Term[] {x}, bool));
+    assertDoesNotThrow(() -> d_solver.synthFun("f2", new Term[] {x}, bool, g1));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.synthFun("f3", new Term[] {nullTerm}, bool));
+    assertThrows(CVC5ApiException.class, () -> d_solver.synthFun("f4", new Term[] {}, nullSort));
+    assertThrows(CVC5ApiException.class, () -> d_solver.synthFun("f6", new Term[] {x}, bool, g2));
+
+    Solver slv = new Solver();
+    Term x2 = slv.mkVar(slv.getBooleanSort());
+    assertDoesNotThrow(() -> slv.synthFun("f1", new Term[] {x2}, slv.getBooleanSort()));
+
+    assertThrows(
+        CVC5ApiException.class, () -> slv.synthFun("", new Term[] {}, d_solver.getBooleanSort()));
+    assertThrows(CVC5ApiException.class,
+        () -> slv.synthFun("f1", new Term[] {x}, d_solver.getBooleanSort()));
+  }
+
+  @Test void synthInv() throws CVC5ApiException
+  {
+    Sort bool = d_solver.getBooleanSort();
+    Sort integer = d_solver.getIntegerSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term x = d_solver.mkVar(bool);
+
+    Term start1 = d_solver.mkVar(bool);
+    Term start2 = d_solver.mkVar(integer);
+
+    Grammar g1 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start1});
+    g1.addRule(start1, d_solver.mkBoolean(false));
+
+    Grammar g2 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start2});
+    g2.addRule(start2, d_solver.mkInteger(0));
+
+    assertDoesNotThrow(() -> d_solver.synthInv("", new Term[] {}));
+    assertDoesNotThrow(() -> d_solver.synthInv("i1", new Term[] {x}));
+    assertDoesNotThrow(() -> d_solver.synthInv("i2", new Term[] {x}, g1));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.synthInv("i3", new Term[] {nullTerm}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.synthInv("i4", new Term[] {x}, g2));
+  }
+
+  @Test void addSygusConstraint() throws CVC5ApiException
+  {
+    Term nullTerm = d_solver.getNullTerm();
+    Term boolTerm = d_solver.mkBoolean(true);
+    Term intTerm = d_solver.mkInteger(1);
+
+    assertDoesNotThrow(() -> d_solver.addSygusConstraint(boolTerm));
+    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusConstraint(nullTerm));
+    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusConstraint(intTerm));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.addSygusConstraint(boolTerm));
+  }
+
+  @Test void addSygusAssume()
+  {
+    Term nullTerm = d_solver.getNullTerm();
+    Term boolTerm = d_solver.mkBoolean(false);
+    Term intTerm = d_solver.mkInteger(1);
+
+    assertDoesNotThrow(() -> d_solver.addSygusAssume(boolTerm));
+    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusAssume(nullTerm));
+    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusAssume(intTerm));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.addSygusAssume(boolTerm));
+  }
+
+  @Test void addSygusInvConstraint() throws CVC5ApiException
+  {
+    Sort bool = d_solver.getBooleanSort();
+    Sort real = d_solver.getRealSort();
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term intTerm = d_solver.mkInteger(1);
+
+    Term inv = d_solver.declareFun("inv", new Sort[] {real}, bool);
+    Term pre = d_solver.declareFun("pre", new Sort[] {real}, bool);
+    Term trans = d_solver.declareFun("trans", new Sort[] {real, real}, bool);
+    Term post = d_solver.declareFun("post", new Sort[] {real}, bool);
+
+    Term inv1 = d_solver.declareFun("inv1", new Sort[] {real}, real);
+
+    Term trans1 = d_solver.declareFun("trans1", new Sort[] {bool, real}, bool);
+    Term trans2 = d_solver.declareFun("trans2", new Sort[] {real, bool}, bool);
+    Term trans3 = d_solver.declareFun("trans3", new Sort[] {real, real}, real);
+
+    assertDoesNotThrow(() -> d_solver.addSygusInvConstraint(inv, pre, trans, post));
+
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(nullTerm, pre, trans, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, nullTerm, trans, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, nullTerm, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans, nullTerm));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(intTerm, pre, trans, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv1, pre, trans, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, trans, trans, post));
+    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, pre, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans1, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans2, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans3, post));
+    assertThrows(
+        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans, trans));
+
+    Solver slv = new Solver();
+    Sort boolean2 = slv.getBooleanSort();
+    Sort real2 = slv.getRealSort();
+    Term inv22 = slv.declareFun("inv", new Sort[] {real2}, boolean2);
+    Term pre22 = slv.declareFun("pre", new Sort[] {real2}, boolean2);
+    Term trans22 = slv.declareFun("trans", new Sort[] {real2, real2}, boolean2);
+    Term post22 = slv.declareFun("post", new Sort[] {real2}, boolean2);
+    assertDoesNotThrow(() -> slv.addSygusInvConstraint(inv22, pre22, trans22, post22));
+
+    assertThrows(
+        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv, pre22, trans22, post22));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv22, pre, trans22, post22));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv22, pre22, trans, post22));
+    assertThrows(
+        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv22, pre22, trans22, post));
+  }
+
+  @Test void getSynthSolution() throws CVC5ApiException
+  {
+    d_solver.setOption("lang", "sygus2");
+    d_solver.setOption("incremental", "false");
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term x = d_solver.mkBoolean(false);
+    Term f = d_solver.synthFun("f", new Term[] {}, d_solver.getBooleanSort());
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolution(f));
+
+    d_solver.checkSynth();
+
+    assertDoesNotThrow(() -> d_solver.getSynthSolution(f));
+    assertDoesNotThrow(() -> d_solver.getSynthSolution(f));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolution(nullTerm));
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolution(x));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.getSynthSolution(f));
+  }
+
+  @Test void getSynthSolutions() throws CVC5ApiException
+  {
+    d_solver.setOption("lang", "sygus2");
+    d_solver.setOption("incremental", "false");
+
+    Term nullTerm = d_solver.getNullTerm();
+    Term x = d_solver.mkBoolean(false);
+    Term f = d_solver.synthFun("f", new Term[] {}, d_solver.getBooleanSort());
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {f}));
+
+    d_solver.checkSynth();
+
+    assertDoesNotThrow(() -> d_solver.getSynthSolutions(new Term[] {f}));
+    assertDoesNotThrow(() -> d_solver.getSynthSolutions(new Term[] {f, f}));
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {nullTerm}));
+    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {x}));
+
+    Solver slv = new Solver();
+    assertThrows(CVC5ApiException.class, () -> slv.getSynthSolutions(new Term[] {x}));
+  }
+
+  @Test void tupleProject() throws CVC5ApiException
+  {
+    Sort[] sorts = new Sort[] {d_solver.getBooleanSort(),
+        d_solver.getIntegerSort(),
+        d_solver.getStringSort(),
+        d_solver.mkSetSort(d_solver.getStringSort())};
+    Term[] elements = new Term[] {d_solver.mkBoolean(true),
+        d_solver.mkInteger(3),
+        d_solver.mkString("C"),
+        d_solver.mkTerm(SINGLETON, d_solver.mkString("Z"))};
+
+    Term tuple = d_solver.mkTuple(sorts, elements);
+
+    int[] indices1 = new int[] {};
+    int[] indices2 = new int[] {0};
+    int[] indices3 = new int[] {0, 1};
+    int[] indices4 = new int[] {0, 0, 2, 2, 3, 3, 0};
+    int[] indices5 = new int[] {4};
+    int[] indices6 = new int[] {0, 4};
+
+    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices1), tuple));
+    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices2), tuple));
+    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices3), tuple));
+    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices4), tuple));
+
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices5), tuple));
+    assertThrows(CVC5ApiException.class,
+        () -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices6), tuple));
+
+    int[] indices = new int[] {0, 3, 2, 0, 1, 2};
+
+    Op op = d_solver.mkOp(TUPLE_PROJECT, indices);
+    Term projection = d_solver.mkTerm(op, tuple);
+
+    Datatype datatype = tuple.getSort().getDatatype();
+    DatatypeConstructor constructor = datatype.getConstructor(0);
+
+    for (int i = 0; i < indices.length; i++)
+    {
+      Term selectorTerm = constructor.getSelector(indices[i]).getSelectorTerm();
+      Term selectedTerm = d_solver.mkTerm(APPLY_SELECTOR, selectorTerm, tuple);
+      Term simplifiedTerm = d_solver.simplify(selectedTerm);
+      assertEquals(elements[indices[i]], simplifiedTerm);
+    }
+
+    assertEquals("((_ tuple_project 0 3 2 0 1 2) (tuple true 3 \"C\" (singleton "
+            + "\"Z\")))",
+        projection.toString());
+  }
+}
diff --git a/test/unit/api/java/SortTest.java b/test/unit/api/java/SortTest.java
new file mode 100644 (file)
index 0000000..6649e5d
--- /dev/null
@@ -0,0 +1,590 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Andrew Reynolds, Mathias Preiner, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the guards of the Java API functions.
+ */
+
+package tests;
+import static io.github.cvc5.api.Kind.*;
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import java.math.BigInteger;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Iterator;
+import java.util.List;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+class SortTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  Sort create_datatype_sort() throws CVC5ApiException
+  {
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    cons.addSelectorSelf("tail");
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    return d_solver.mkDatatypeSort(dtypeSpec);
+  }
+
+  Sort create_param_datatype_sort() throws CVC5ApiException
+  {
+    Sort sort = d_solver.mkParamSort("T");
+    DatatypeDecl paramDtypeSpec = d_solver.mkDatatypeDecl("paramlist", sort);
+    DatatypeConstructorDecl paramCons = d_solver.mkDatatypeConstructorDecl("cons");
+    DatatypeConstructorDecl paramNil = d_solver.mkDatatypeConstructorDecl("nil");
+    paramCons.addSelector("head", sort);
+    paramDtypeSpec.addConstructor(paramCons);
+    paramDtypeSpec.addConstructor(paramNil);
+    return d_solver.mkDatatypeSort(paramDtypeSpec);
+  }
+
+  @Test void operators_comparison()
+  {
+    assertDoesNotThrow(() -> d_solver.getIntegerSort() == d_solver.getNullSort());
+    assertDoesNotThrow(() -> d_solver.getIntegerSort() != d_solver.getNullSort());
+    assertDoesNotThrow(() -> d_solver.getIntegerSort().compareTo(d_solver.getNullSort()));
+  }
+
+  @Test void isBoolean()
+  {
+    assertTrue(d_solver.getBooleanSort().isBoolean());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isBoolean());
+  }
+
+  @Test void isInteger()
+  {
+    assertTrue(d_solver.getIntegerSort().isInteger());
+    assertTrue(!d_solver.getRealSort().isInteger());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isInteger());
+  }
+
+  @Test void isReal()
+  {
+    assertTrue(d_solver.getRealSort().isReal());
+    assertTrue(!d_solver.getIntegerSort().isReal());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isReal());
+  }
+
+  @Test void isString()
+  {
+    assertTrue(d_solver.getStringSort().isString());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isString());
+  }
+
+  @Test void isRegExp()
+  {
+    assertTrue(d_solver.getRegExpSort().isRegExp());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isRegExp());
+  }
+
+  @Test void isRoundingMode() throws CVC5ApiException
+  {
+    assertTrue(d_solver.getRoundingModeSort().isRoundingMode());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isRoundingMode());
+  }
+
+  @Test void isBitVector() throws CVC5ApiException
+  {
+    assertTrue(d_solver.mkBitVectorSort(8).isBitVector());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isBitVector());
+  }
+
+  @Test void isFloatingPoint() throws CVC5ApiException
+  {
+    assertTrue(d_solver.mkFloatingPointSort(8, 24).isFloatingPoint());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isFloatingPoint());
+  }
+
+  @Test void isDatatype() throws CVC5ApiException
+  {
+    Sort dt_sort = create_datatype_sort();
+    assertTrue(dt_sort.isDatatype());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isDatatype());
+  }
+
+  @Test void isParametricDatatype() throws CVC5ApiException
+  {
+    Sort param_dt_sort = create_param_datatype_sort();
+    assertTrue(param_dt_sort.isParametricDatatype());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isParametricDatatype());
+  }
+
+  @Test void isConstructor() throws CVC5ApiException
+  {
+    Sort dt_sort = create_datatype_sort();
+    Datatype dt = dt_sort.getDatatype();
+    Sort cons_sort = dt.getConstructor(0).getConstructorTerm().getSort();
+    assertTrue(cons_sort.isConstructor());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isConstructor());
+  }
+
+  @Test void isSelector() throws CVC5ApiException
+  {
+    Sort dt_sort = create_datatype_sort();
+    Datatype dt = dt_sort.getDatatype();
+    Sort cons_sort = dt.getConstructor(0).getSelector(1).getSelectorTerm().getSort();
+    assertTrue(cons_sort.isSelector());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isSelector());
+  }
+
+  @Test void isTester() throws CVC5ApiException
+  {
+    Sort dt_sort = create_datatype_sort();
+    Datatype dt = dt_sort.getDatatype();
+    Sort cons_sort = dt.getConstructor(0).getTesterTerm().getSort();
+    assertTrue(cons_sort.isTester());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isTester());
+  }
+
+  @Test void isFunction()
+  {
+    Sort fun_sort = d_solver.mkFunctionSort(d_solver.getRealSort(), d_solver.getIntegerSort());
+    assertTrue(fun_sort.isFunction());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isFunction());
+  }
+
+  @Test void isPredicate()
+  {
+    Sort pred_sort = d_solver.mkPredicateSort(new Sort[] {d_solver.getRealSort()});
+    assertTrue(pred_sort.isPredicate());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isPredicate());
+  }
+
+  @Test void isTuple()
+  {
+    Sort tup_sort = d_solver.mkTupleSort(new Sort[] {d_solver.getRealSort()});
+    assertTrue(tup_sort.isTuple());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isTuple());
+  }
+
+  @Test void isRecord()
+  {
+    Sort rec_sort =
+        d_solver.mkRecordSort(new Pair[] {new Pair<String, Sort>("asdf", d_solver.getRealSort())});
+    assertTrue(rec_sort.isRecord());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isRecord());
+  }
+
+  @Test void isArray()
+  {
+    Sort arr_sort = d_solver.mkArraySort(d_solver.getRealSort(), d_solver.getIntegerSort());
+    assertTrue(arr_sort.isArray());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isArray());
+  }
+
+  @Test void isSet()
+  {
+    Sort set_sort = d_solver.mkSetSort(d_solver.getRealSort());
+    assertTrue(set_sort.isSet());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isSet());
+  }
+
+  @Test void isBag()
+  {
+    Sort bag_sort = d_solver.mkBagSort(d_solver.getRealSort());
+    assertTrue(bag_sort.isBag());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isBag());
+  }
+
+  @Test void isSequence()
+  {
+    Sort seq_sort = d_solver.mkSequenceSort(d_solver.getRealSort());
+    assertTrue(seq_sort.isSequence());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isSequence());
+  }
+
+  @Test void isUninterpreted()
+  {
+    Sort un_sort = d_solver.mkUninterpretedSort("asdf");
+    assertTrue(un_sort.isUninterpretedSort());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isUninterpretedSort());
+  }
+
+  @Test void isSortConstructor() throws CVC5ApiException
+  {
+    Sort sc_sort = d_solver.mkSortConstructorSort("asdf", 1);
+    assertTrue(sc_sort.isSortConstructor());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isSortConstructor());
+  }
+
+  @Test void isFirstClass()
+  {
+    Sort fun_sort = d_solver.mkFunctionSort(d_solver.getRealSort(), d_solver.getIntegerSort());
+    assertTrue(d_solver.getIntegerSort().isFirstClass());
+    assertTrue(fun_sort.isFirstClass());
+    Sort reSort = d_solver.getRegExpSort();
+    assertFalse(reSort.isFirstClass());
+    assertDoesNotThrow(() -> d_solver.getNullSort().isFirstClass());
+  }
+
+  @Test void isFunctionLike() throws CVC5ApiException
+  {
+    Sort fun_sort = d_solver.mkFunctionSort(d_solver.getRealSort(), d_solver.getIntegerSort());
+    assertFalse(d_solver.getIntegerSort().isFunctionLike());
+    assertTrue(fun_sort.isFunctionLike());
+
+    Sort dt_sort = create_datatype_sort();
+    Datatype dt = dt_sort.getDatatype();
+    Sort cons_sort = dt.getConstructor(0).getSelector(1).getSelectorTerm().getSort();
+    assertTrue(cons_sort.isFunctionLike());
+
+    assertDoesNotThrow(() -> d_solver.getNullSort().isFunctionLike());
+  }
+
+  @Test void isSubsortOf()
+  {
+    assertTrue(d_solver.getIntegerSort().isSubsortOf(d_solver.getIntegerSort()));
+    assertTrue(d_solver.getIntegerSort().isSubsortOf(d_solver.getRealSort()));
+    assertFalse(d_solver.getIntegerSort().isSubsortOf(d_solver.getBooleanSort()));
+    assertDoesNotThrow(() -> d_solver.getNullSort().isSubsortOf(d_solver.getNullSort()));
+  }
+
+  @Test void isComparableTo()
+  {
+    assertTrue(d_solver.getIntegerSort().isComparableTo(d_solver.getIntegerSort()));
+    assertTrue(d_solver.getIntegerSort().isComparableTo(d_solver.getRealSort()));
+    assertFalse(d_solver.getIntegerSort().isComparableTo(d_solver.getBooleanSort()));
+    assertDoesNotThrow(() -> d_solver.getNullSort().isComparableTo(d_solver.getNullSort()));
+  }
+
+  @Test void getDatatype() throws CVC5ApiException
+  {
+    Sort dtypeSort = create_datatype_sort();
+    assertDoesNotThrow(() -> dtypeSort.getDatatype());
+    // create bv sort, check should fail
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getDatatype());
+  }
+
+  @Test void datatypeSorts() throws CVC5ApiException
+  {
+    Sort intSort = d_solver.getIntegerSort();
+    Sort dtypeSort = create_datatype_sort();
+    Datatype dt = dtypeSort.getDatatype();
+    assertFalse(dtypeSort.isConstructor());
+    assertThrows(CVC5ApiException.class, () -> dtypeSort.getConstructorCodomainSort());
+    assertThrows(CVC5ApiException.class, () -> dtypeSort.getConstructorDomainSorts());
+    assertThrows(CVC5ApiException.class, () -> dtypeSort.getConstructorArity());
+
+    // get constructor
+    DatatypeConstructor dcons = dt.getConstructor(0);
+    Term consTerm = dcons.getConstructorTerm();
+    Sort consSort = consTerm.getSort();
+    assertTrue(consSort.isConstructor());
+    assertFalse(consSort.isTester());
+    assertFalse(consSort.isSelector());
+    assertEquals(consSort.getConstructorArity(), 2);
+    Sort[] consDomSorts = consSort.getConstructorDomainSorts();
+    assertEquals(consDomSorts[0], intSort);
+    assertEquals(consDomSorts[1], dtypeSort);
+    assertEquals(consSort.getConstructorCodomainSort(), dtypeSort);
+
+    // get tester
+    Term isConsTerm = dcons.getTesterTerm();
+    assertTrue(isConsTerm.getSort().isTester());
+    assertEquals(isConsTerm.getSort().getTesterDomainSort(), dtypeSort);
+    Sort booleanSort = d_solver.getBooleanSort();
+    assertEquals(isConsTerm.getSort().getTesterCodomainSort(), booleanSort);
+    assertThrows(CVC5ApiException.class, () -> booleanSort.getTesterDomainSort());
+    assertThrows(CVC5ApiException.class, () -> booleanSort.getTesterCodomainSort());
+
+    // get selector
+    DatatypeSelector dselTail = dcons.getSelector(1);
+    Term tailTerm = dselTail.getSelectorTerm();
+    assertTrue(tailTerm.getSort().isSelector());
+    assertEquals(tailTerm.getSort().getSelectorDomainSort(), dtypeSort);
+    assertEquals(tailTerm.getSort().getSelectorCodomainSort(), dtypeSort);
+    assertThrows(CVC5ApiException.class, () -> booleanSort.getSelectorDomainSort());
+    assertThrows(CVC5ApiException.class, () -> booleanSort.getSelectorCodomainSort());
+  }
+
+  @Test void instantiate() throws CVC5ApiException
+  {
+    // instantiate parametric datatype, check should not fail
+    Sort paramDtypeSort = create_param_datatype_sort();
+    assertDoesNotThrow(() -> paramDtypeSort.instantiate(new Sort[] {d_solver.getIntegerSort()}));
+    // instantiate non-parametric datatype sort, check should fail
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
+    assertThrows(CVC5ApiException.class,
+        () -> dtypeSort.instantiate(new Sort[] {d_solver.getIntegerSort()}));
+  }
+
+  @Test void getFunctionArity() throws CVC5ApiException
+  {
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    assertDoesNotThrow(() -> funSort.getFunctionArity());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getFunctionArity());
+  }
+
+  @Test void getFunctionDomainSorts() throws CVC5ApiException
+  {
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    assertDoesNotThrow(() -> funSort.getFunctionDomainSorts());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getFunctionDomainSorts());
+  }
+
+  @Test void getFunctionCodomainSort() throws CVC5ApiException
+  {
+    Sort funSort =
+        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
+    assertDoesNotThrow(() -> funSort.getFunctionCodomainSort());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getFunctionCodomainSort());
+  }
+
+  @Test void getArrayIndexSort() throws CVC5ApiException
+  {
+    Sort elementSort = d_solver.mkBitVectorSort(32);
+    Sort indexSort = d_solver.mkBitVectorSort(32);
+    Sort arraySort = d_solver.mkArraySort(indexSort, elementSort);
+    assertDoesNotThrow(() -> arraySort.getArrayIndexSort());
+    assertThrows(CVC5ApiException.class, () -> indexSort.getArrayIndexSort());
+  }
+
+  @Test void getArrayElementSort() throws CVC5ApiException
+  {
+    Sort elementSort = d_solver.mkBitVectorSort(32);
+    Sort indexSort = d_solver.mkBitVectorSort(32);
+    Sort arraySort = d_solver.mkArraySort(indexSort, elementSort);
+    assertDoesNotThrow(() -> arraySort.getArrayElementSort());
+    assertThrows(CVC5ApiException.class, () -> indexSort.getArrayElementSort());
+  }
+
+  @Test void getSetElementSort() throws CVC5ApiException
+  {
+    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
+    assertDoesNotThrow(() -> setSort.getSetElementSort());
+    Sort elementSort = setSort.getSetElementSort();
+    assertEquals(elementSort, d_solver.getIntegerSort());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getSetElementSort());
+  }
+
+  @Test void getBagElementSort() throws CVC5ApiException
+  {
+    Sort bagSort = d_solver.mkBagSort(d_solver.getIntegerSort());
+    assertDoesNotThrow(() -> bagSort.getBagElementSort());
+    Sort elementSort = bagSort.getBagElementSort();
+    assertEquals(elementSort, d_solver.getIntegerSort());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getBagElementSort());
+  }
+
+  @Test void getSequenceElementSort() throws CVC5ApiException
+  {
+    Sort seqSort = d_solver.mkSequenceSort(d_solver.getIntegerSort());
+    assertTrue(seqSort.isSequence());
+    assertDoesNotThrow(() -> seqSort.getSequenceElementSort());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertFalse(bvSort.isSequence());
+    assertThrows(CVC5ApiException.class, () -> bvSort.getSequenceElementSort());
+  }
+
+  @Test void getUninterpretedSortName() throws CVC5ApiException
+  {
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    assertDoesNotThrow(() -> uSort.getUninterpretedSortName());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getUninterpretedSortName());
+  }
+
+  @Test void isUninterpretedSortParameterized() throws CVC5ApiException
+  {
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    assertFalse(uSort.isUninterpretedSortParameterized());
+    Sort sSort = d_solver.mkSortConstructorSort("s", 1);
+    Sort siSort = sSort.instantiate(new Sort[] {uSort});
+    assertTrue(siSort.isUninterpretedSortParameterized());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.isUninterpretedSortParameterized());
+  }
+
+  @Test void getUninterpretedSortParamSorts() throws CVC5ApiException
+  {
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    assertDoesNotThrow(() -> uSort.getUninterpretedSortParamSorts());
+    Sort sSort = d_solver.mkSortConstructorSort("s", 2);
+    Sort siSort = sSort.instantiate(new Sort[] {uSort, uSort});
+    assertEquals(siSort.getUninterpretedSortParamSorts().length, 2);
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getUninterpretedSortParamSorts());
+  }
+
+  @Test void getUninterpretedSortConstructorName() throws CVC5ApiException
+  {
+    Sort sSort = d_solver.mkSortConstructorSort("s", 2);
+    assertDoesNotThrow(() -> sSort.getSortConstructorName());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getSortConstructorName());
+  }
+
+  @Test void getUninterpretedSortConstructorArity() throws CVC5ApiException
+  {
+    Sort sSort = d_solver.mkSortConstructorSort("s", 2);
+    assertDoesNotThrow(() -> sSort.getSortConstructorArity());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getSortConstructorArity());
+  }
+
+  @Test void getBitVectorSize() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertDoesNotThrow(() -> bvSort.getBitVectorSize());
+    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
+    assertThrows(CVC5ApiException.class, () -> setSort.getBitVectorSize());
+  }
+
+  @Test void getFloatingPointExponentSize() throws CVC5ApiException
+  {
+    Sort fpSort = d_solver.mkFloatingPointSort(4, 8);
+    assertDoesNotThrow(() -> fpSort.getFloatingPointExponentSize());
+    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
+    assertThrows(CVC5ApiException.class, () -> setSort.getFloatingPointExponentSize());
+  }
+
+  @Test void getFloatingPointSignificandSize() throws CVC5ApiException
+  {
+    Sort fpSort = d_solver.mkFloatingPointSort(4, 8);
+    assertDoesNotThrow(() -> fpSort.getFloatingPointSignificandSize());
+    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
+    assertThrows(CVC5ApiException.class, () -> setSort.getFloatingPointSignificandSize());
+  }
+
+  @Test void getDatatypeParamSorts() throws CVC5ApiException
+  {
+    // create parametric datatype, check should not fail
+    Sort sort = d_solver.mkParamSort("T");
+    DatatypeDecl paramDtypeSpec = d_solver.mkDatatypeDecl("paramlist", sort);
+    DatatypeConstructorDecl paramCons = d_solver.mkDatatypeConstructorDecl("cons");
+    DatatypeConstructorDecl paramNil = d_solver.mkDatatypeConstructorDecl("nil");
+    paramCons.addSelector("head", sort);
+    paramDtypeSpec.addConstructor(paramCons);
+    paramDtypeSpec.addConstructor(paramNil);
+    Sort paramDtypeSort = d_solver.mkDatatypeSort(paramDtypeSpec);
+    assertDoesNotThrow(() -> paramDtypeSort.getDatatypeParamSorts());
+    // create non-parametric datatype sort, check should fail
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
+    assertThrows(CVC5ApiException.class, () -> dtypeSort.getDatatypeParamSorts());
+  }
+
+  @Test void getDatatypeArity() throws CVC5ApiException
+  {
+    // create datatype sort, check should not fail
+    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    cons.addSelector("head", d_solver.getIntegerSort());
+    dtypeSpec.addConstructor(cons);
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    dtypeSpec.addConstructor(nil);
+    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
+    assertDoesNotThrow(() -> dtypeSort.getDatatypeArity());
+    // create bv sort, check should fail
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getDatatypeArity());
+  }
+
+  @Test void getTupleLength() throws CVC5ApiException
+  {
+    Sort tupleSort =
+        d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort(), d_solver.getIntegerSort()});
+    assertDoesNotThrow(() -> tupleSort.getTupleLength());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getTupleLength());
+  }
+
+  @Test void getTupleSorts() throws CVC5ApiException
+  {
+    Sort tupleSort =
+        d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort(), d_solver.getIntegerSort()});
+    assertDoesNotThrow(() -> tupleSort.getTupleSorts());
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    assertThrows(CVC5ApiException.class, () -> bvSort.getTupleSorts());
+  }
+
+  @Test void sortCompare() throws CVC5ApiException
+  {
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort intSort = d_solver.getIntegerSort();
+    Sort bvSort = d_solver.mkBitVectorSort(32);
+    Sort bvSort2 = d_solver.mkBitVectorSort(32);
+    assertTrue(bvSort.compareTo(bvSort2) >= 0);
+    assertTrue(bvSort.compareTo(bvSort2) <= 0);
+    assertTrue(intSort.compareTo(boolSort) > 0 != intSort.compareTo(boolSort) < 0);
+    assertTrue((intSort.compareTo(bvSort) > 0 || intSort.equals(bvSort))
+        == (intSort.compareTo(bvSort) >= 0));
+  }
+
+  @Test void sortSubtyping()
+  {
+    Sort intSort = d_solver.getIntegerSort();
+    Sort realSort = d_solver.getRealSort();
+    assertTrue(intSort.isSubsortOf(realSort));
+    assertFalse(realSort.isSubsortOf(intSort));
+    assertTrue(intSort.isComparableTo(realSort));
+    assertTrue(realSort.isComparableTo(intSort));
+
+    Sort arraySortII = d_solver.mkArraySort(intSort, intSort);
+    Sort arraySortIR = d_solver.mkArraySort(intSort, realSort);
+    assertFalse(arraySortII.isComparableTo(intSort));
+    // we do not support subtyping for arrays
+    assertFalse(arraySortII.isComparableTo(arraySortIR));
+
+    Sort setSortI = d_solver.mkSetSort(intSort);
+    Sort setSortR = d_solver.mkSetSort(realSort);
+    // we don't support subtyping for sets
+    assertFalse(setSortI.isComparableTo(setSortR));
+    assertFalse(setSortI.isSubsortOf(setSortR));
+    assertFalse(setSortR.isComparableTo(setSortI));
+    assertFalse(setSortR.isSubsortOf(setSortI));
+  }
+
+  @Test void sortScopedToString() throws CVC5ApiException
+  {
+    String name = "uninterp-sort";
+    Sort bvsort8 = d_solver.mkBitVectorSort(8);
+    Sort uninterp_sort = d_solver.mkUninterpretedSort(name);
+    assertEquals(bvsort8.toString(), "(_ BitVec 8)");
+    assertEquals(uninterp_sort.toString(), name);
+    Solver solver2;
+    assertEquals(bvsort8.toString(), "(_ BitVec 8)");
+    assertEquals(uninterp_sort.toString(), name);
+  }
+}
diff --git a/test/unit/api/java/TermTest.java b/test/unit/api/java/TermTest.java
new file mode 100644 (file)
index 0000000..cb59849
--- /dev/null
@@ -0,0 +1,1059 @@
+/******************************************************************************
+ * Top contributors (to current version):
+ *   Aina Niemetz, Makai Mann, Andrew Reynolds, Mudathir Mohamed
+ *
+ * This file is part of the cvc5 project.
+ *
+ * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
+ * in the top-level source directory and their institutional affiliations.
+ * All rights reserved.  See the file COPYING in the top-level source
+ * directory for licensing information.
+ * ****************************************************************************
+ *
+ * Black box testing of the Term class.
+ */
+
+package tests;
+import static io.github.cvc5.api.Kind.*;
+import static org.junit.jupiter.api.Assertions.*;
+
+import io.github.cvc5.api.*;
+import java.math.BigInteger;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+
+class TermTest
+{
+  private Solver d_solver;
+
+  @BeforeEach void setUp()
+  {
+    d_solver = new Solver();
+  }
+
+  @Test void eq()
+  {
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Term x = d_solver.mkVar(uSort, "x");
+    Term y = d_solver.mkVar(uSort, "y");
+    Term z = d_solver.getNullTerm();
+
+    assertTrue(x == x);
+    assertFalse(x != x);
+    assertFalse(x == y);
+    assertTrue(x != y);
+    assertFalse((x == z));
+    assertTrue(x != z);
+  }
+
+  @Test void getId()
+  {
+    Term n = d_solver.getNullTerm();
+    assertThrows(CVC5ApiException.class, () -> n.getId());
+    Term x = d_solver.mkVar(d_solver.getIntegerSort(), "x");
+    assertDoesNotThrow(() -> x.getId());
+    Term y = x;
+    assertEquals(x.getId(), y.getId());
+
+    Term z = d_solver.mkVar(d_solver.getIntegerSort(), "z");
+    assertNotEquals(x.getId(), z.getId());
+  }
+
+  @Test void getKind() throws CVC5ApiException
+  {
+    Sort uSort = d_solver.mkUninterpretedSort("u");
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(uSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term n = d_solver.getNullTerm();
+    assertThrows(CVC5ApiException.class, () -> n.getKind());
+    Term x = d_solver.mkVar(uSort, "x");
+    assertDoesNotThrow(() -> x.getKind());
+    Term y = d_solver.mkVar(uSort, "y");
+    assertDoesNotThrow(() -> y.getKind());
+
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertDoesNotThrow(() -> f.getKind());
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertDoesNotThrow(() -> p.getKind());
+
+    Term zero = d_solver.mkInteger(0);
+    assertDoesNotThrow(() -> zero.getKind());
+
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertDoesNotThrow(() -> f_x.getKind());
+    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
+    assertDoesNotThrow(() -> f_y.getKind());
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
+    assertDoesNotThrow(() -> sum.getKind());
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.getKind());
+    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
+    assertDoesNotThrow(() -> p_f_y.getKind());
+
+    // Sequence kinds do not exist internally, test that the API properly
+    // converts them back.
+    Sort seqSort = d_solver.mkSequenceSort(intSort);
+    Term s = d_solver.mkConst(seqSort, "s");
+    Term ss = d_solver.mkTerm(SEQ_CONCAT, s, s);
+    assertEquals(ss.getKind(), SEQ_CONCAT);
+  }
+
+  @Test void getSort() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term n = d_solver.getNullTerm();
+    assertThrows(CVC5ApiException.class, () -> n.getSort());
+    Term x = d_solver.mkVar(bvSort, "x");
+    assertDoesNotThrow(() -> x.getSort());
+    assertEquals(x.getSort(), bvSort);
+    Term y = d_solver.mkVar(bvSort, "y");
+    assertDoesNotThrow(() -> y.getSort());
+    assertEquals(y.getSort(), bvSort);
+
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertDoesNotThrow(() -> f.getSort());
+    assertEquals(f.getSort(), funSort1);
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertDoesNotThrow(() -> p.getSort());
+    assertEquals(p.getSort(), funSort2);
+
+    Term zero = d_solver.mkInteger(0);
+    assertDoesNotThrow(() -> zero.getSort());
+    assertEquals(zero.getSort(), intSort);
+
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertDoesNotThrow(() -> f_x.getSort());
+    assertEquals(f_x.getSort(), intSort);
+    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
+    assertDoesNotThrow(() -> f_y.getSort());
+    assertEquals(f_y.getSort(), intSort);
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
+    assertDoesNotThrow(() -> sum.getSort());
+    assertEquals(sum.getSort(), intSort);
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.getSort());
+    assertEquals(p_0.getSort(), boolSort);
+    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
+    assertDoesNotThrow(() -> p_f_y.getSort());
+    assertEquals(p_f_y.getSort(), boolSort);
+  }
+
+  @Test void getOp() throws CVC5ApiException
+  {
+    Sort intsort = d_solver.getIntegerSort();
+    Sort bvsort = d_solver.mkBitVectorSort(8);
+    Sort arrsort = d_solver.mkArraySort(bvsort, intsort);
+    Sort funsort = d_solver.mkFunctionSort(intsort, bvsort);
+
+    Term x = d_solver.mkConst(intsort, "x");
+    Term a = d_solver.mkConst(arrsort, "a");
+    Term b = d_solver.mkConst(bvsort, "b");
+
+    assertFalse(x.hasOp());
+    assertThrows(CVC5ApiException.class, () -> x.getOp());
+
+    Term ab = d_solver.mkTerm(SELECT, a, b);
+    Op ext = d_solver.mkOp(BITVECTOR_EXTRACT, 4, 0);
+    Term extb = d_solver.mkTerm(ext, b);
+
+    assertTrue(ab.hasOp());
+    assertFalse(ab.getOp().isIndexed());
+    // can compare directly to a Kind (will invoke Op constructor)
+    assertTrue(extb.hasOp());
+    assertTrue(extb.getOp().isIndexed());
+    assertEquals(extb.getOp(), ext);
+
+    Term f = d_solver.mkConst(funsort, "f");
+    Term fx = d_solver.mkTerm(APPLY_UF, f, x);
+
+    assertFalse(f.hasOp());
+    assertThrows(CVC5ApiException.class, () -> f.getOp());
+    assertTrue(fx.hasOp());
+    List<Term> children = new ArrayList();
+
+    Iterator<Term> iterator = fx.iterator();
+    for (Term t : fx)
+    {
+      children.add(t);
+    }
+
+    // testing rebuild from op and children
+    assertEquals(fx, d_solver.mkTerm(fx.getOp(), children));
+
+    // Test Datatypes Ops
+    Sort sort = d_solver.mkParamSort("T");
+    DatatypeDecl listDecl = d_solver.mkDatatypeDecl("paramlist", sort);
+    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
+    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
+    cons.addSelector("head", sort);
+    cons.addSelectorSelf("tail");
+    listDecl.addConstructor(cons);
+    listDecl.addConstructor(nil);
+    Sort listSort = d_solver.mkDatatypeSort(listDecl);
+    Sort intListSort = listSort.instantiate(new Sort[] {d_solver.getIntegerSort()});
+    Term c = d_solver.mkConst(intListSort, "c");
+    Datatype list = listSort.getDatatype();
+    // list datatype constructor and selector operator terms
+    Term consOpTerm = list.getConstructorTerm("cons");
+    Term nilOpTerm = list.getConstructorTerm("nil");
+  }
+
+  @Test void isNull() throws CVC5ApiException
+  {
+    Term x = d_solver.getNullTerm();
+    assertTrue(x.isNull());
+    x = d_solver.mkVar(d_solver.mkBitVectorSort(4), "x");
+    assertFalse(x.isNull());
+  }
+
+  @Test void notTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().notTerm());
+    Term b = d_solver.mkTrue();
+    assertDoesNotThrow(() -> b.notTerm());
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertThrows(CVC5ApiException.class, () -> x.notTerm());
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.notTerm());
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.notTerm());
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.notTerm());
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.notTerm());
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.notTerm());
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.notTerm());
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.notTerm());
+  }
+
+  @Test void andTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term b = d_solver.mkTrue();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> b.andTerm(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> b.andTerm(b));
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertThrows(CVC5ApiException.class, () -> x.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> x.andTerm(x));
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f.andTerm(f));
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p.andTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p.andTerm(p));
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> zero.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> zero.andTerm(f));
+    assertThrows(CVC5ApiException.class, () -> zero.andTerm(p));
+    assertThrows(CVC5ApiException.class, () -> zero.andTerm(zero));
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(f));
+    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(p));
+    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(f_x));
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(f));
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(p));
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> sum.andTerm(sum));
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(sum));
+    assertDoesNotThrow(() -> p_0.andTerm(p_0));
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.andTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(sum));
+    assertDoesNotThrow(() -> p_f_x.andTerm(p_0));
+    assertDoesNotThrow(() -> p_f_x.andTerm(p_f_x));
+  }
+
+  @Test void orTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term b = d_solver.mkTrue();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> b.orTerm(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> b.orTerm(b));
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertThrows(CVC5ApiException.class, () -> x.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> x.orTerm(x));
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f.orTerm(f));
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p.orTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p.orTerm(p));
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> zero.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> zero.orTerm(f));
+    assertThrows(CVC5ApiException.class, () -> zero.orTerm(p));
+    assertThrows(CVC5ApiException.class, () -> zero.orTerm(zero));
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(f));
+    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(p));
+    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(f_x));
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(f));
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(p));
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> sum.orTerm(sum));
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(sum));
+    assertDoesNotThrow(() -> p_0.orTerm(p_0));
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.orTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(sum));
+    assertDoesNotThrow(() -> p_f_x.orTerm(p_0));
+    assertDoesNotThrow(() -> p_f_x.orTerm(p_f_x));
+  }
+
+  @Test void xorTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term b = d_solver.mkTrue();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> b.xorTerm(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> b.xorTerm(b));
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertThrows(CVC5ApiException.class, () -> x.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> x.xorTerm(x));
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f.xorTerm(f));
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p.xorTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p.xorTerm(p));
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(f));
+    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(p));
+    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(zero));
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(f));
+    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(p));
+    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(f_x));
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(f));
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(p));
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(sum));
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(sum));
+    assertDoesNotThrow(() -> p_0.xorTerm(p_0));
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.xorTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(sum));
+    assertDoesNotThrow(() -> p_f_x.xorTerm(p_0));
+    assertDoesNotThrow(() -> p_f_x.xorTerm(p_f_x));
+  }
+
+  @Test void eqTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term b = d_solver.mkTrue();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> b.eqTerm(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> b.eqTerm(b));
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertThrows(CVC5ApiException.class, () -> x.eqTerm(b));
+    assertDoesNotThrow(() -> x.eqTerm(x));
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f.eqTerm(x));
+    assertDoesNotThrow(() -> f.eqTerm(f));
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p.eqTerm(f));
+    assertDoesNotThrow(() -> p.eqTerm(p));
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(f));
+    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(p));
+    assertDoesNotThrow(() -> zero.eqTerm(zero));
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(f));
+    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(p));
+    assertDoesNotThrow(() -> f_x.eqTerm(zero));
+    assertDoesNotThrow(() -> f_x.eqTerm(f_x));
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(f));
+    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(p));
+    assertDoesNotThrow(() -> sum.eqTerm(zero));
+    assertDoesNotThrow(() -> sum.eqTerm(f_x));
+    assertDoesNotThrow(() -> sum.eqTerm(sum));
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(sum));
+    assertDoesNotThrow(() -> p_0.eqTerm(p_0));
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.eqTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(sum));
+    assertDoesNotThrow(() -> p_f_x.eqTerm(p_0));
+    assertDoesNotThrow(() -> p_f_x.eqTerm(p_f_x));
+  }
+
+  @Test void impTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term b = d_solver.mkTrue();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> b.impTerm(d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> b.impTerm(b));
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertThrows(CVC5ApiException.class, () -> x.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> x.impTerm(x));
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f.impTerm(f));
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p.impTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p.impTerm(p));
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> zero.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> zero.impTerm(f));
+    assertThrows(CVC5ApiException.class, () -> zero.impTerm(p));
+    assertThrows(CVC5ApiException.class, () -> zero.impTerm(zero));
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(f));
+    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(p));
+    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(f_x));
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(f));
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(p));
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> sum.impTerm(sum));
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(sum));
+    assertDoesNotThrow(() -> p_0.impTerm(p_0));
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.impTerm(b));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(f));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(p));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(zero));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(f_x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(sum));
+    assertDoesNotThrow(() -> p_f_x.impTerm(p_0));
+    assertDoesNotThrow(() -> p_f_x.impTerm(p_f_x));
+  }
+
+  @Test void iteTerm() throws CVC5ApiException
+  {
+    Sort bvSort = d_solver.mkBitVectorSort(8);
+    Sort intSort = d_solver.getIntegerSort();
+    Sort boolSort = d_solver.getBooleanSort();
+    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
+    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
+
+    Term b = d_solver.mkTrue();
+    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().iteTerm(b, b));
+    assertThrows(CVC5ApiException.class, () -> b.iteTerm(d_solver.getNullTerm(), b));
+    assertThrows(CVC5ApiException.class, () -> b.iteTerm(b, d_solver.getNullTerm()));
+    assertDoesNotThrow(() -> b.iteTerm(b, b));
+    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
+    assertDoesNotThrow(() -> b.iteTerm(x, x));
+    assertDoesNotThrow(() -> b.iteTerm(b, b));
+    assertThrows(CVC5ApiException.class, () -> b.iteTerm(x, b));
+    assertThrows(CVC5ApiException.class, () -> x.iteTerm(x, x));
+    assertThrows(CVC5ApiException.class, () -> x.iteTerm(x, b));
+    Term f = d_solver.mkVar(funSort1, "f");
+    assertThrows(CVC5ApiException.class, () -> f.iteTerm(b, b));
+    assertThrows(CVC5ApiException.class, () -> x.iteTerm(b, x));
+    Term p = d_solver.mkVar(funSort2, "p");
+    assertThrows(CVC5ApiException.class, () -> p.iteTerm(b, b));
+    assertThrows(CVC5ApiException.class, () -> p.iteTerm(x, b));
+    Term zero = d_solver.mkInteger(0);
+    assertThrows(CVC5ApiException.class, () -> zero.iteTerm(x, x));
+    assertThrows(CVC5ApiException.class, () -> zero.iteTerm(x, b));
+    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
+    assertThrows(CVC5ApiException.class, () -> f_x.iteTerm(b, b));
+    assertThrows(CVC5ApiException.class, () -> f_x.iteTerm(b, x));
+    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
+    assertThrows(CVC5ApiException.class, () -> sum.iteTerm(x, x));
+    assertThrows(CVC5ApiException.class, () -> sum.iteTerm(b, x));
+    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
+    assertDoesNotThrow(() -> p_0.iteTerm(b, b));
+    assertDoesNotThrow(() -> p_0.iteTerm(x, x));
+    assertThrows(CVC5ApiException.class, () -> p_0.iteTerm(x, b));
+    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
+    assertDoesNotThrow(() -> p_f_x.iteTerm(b, b));
+    assertDoesNotThrow(() -> p_f_x.iteTerm(x, x));
+    assertThrows(CVC5ApiException.class, () -> p_f_x.iteTerm(x, b));
+  }
+
+  @Test void termAssignment()
+  {
+    Term t1 = d_solver.mkInteger(1);
+    Term t2 = t1;
+    t2 = d_solver.mkInteger(2);
+    assertEquals(t1, d_solver.mkInteger(1));
+  }
+
+  @Test void termCompare()
+  {
+    Term t1 = d_solver.mkInteger(1);
+    Term t2 = d_solver.mkTerm(PLUS, d_solver.mkInteger(2), d_solver.mkInteger(2));
+    Term t3 = d_solver.mkTerm(PLUS, d_solver.mkInteger(2), d_solver.mkInteger(2));
+    assertTrue(t2.compareTo(t3) >= 0);
+    assertTrue(t2.compareTo(t3) <= 0);
+    assertTrue((t1.compareTo(t2) > 0) != (t1.compareTo(t2) < 0));
+    assertTrue((t1.compareTo(t2) > 0 || t1.equals(t2)) == (t1.compareTo(t2) >= 0));
+  }
+
+  @Test void termChildren() throws CVC5ApiException
+  {
+    // simple term 2+3
+    Term two = d_solver.mkInteger(2);
+    Term t1 = d_solver.mkTerm(PLUS, two, d_solver.mkInteger(3));
+    assertEquals(t1.getChild(0), two);
+    assertEquals(t1.getNumChildren(), 2);
+    Term tnull = d_solver.getNullTerm();
+    assertThrows(CVC5ApiException.class, () -> tnull.getNumChildren());
+
+    // apply term f(2)
+    Sort intSort = d_solver.getIntegerSort();
+    Sort fsort = d_solver.mkFunctionSort(intSort, intSort);
+    Term f = d_solver.mkConst(fsort, "f");
+    Term t2 = d_solver.mkTerm(APPLY_UF, f, two);
+    // due to our higher-order view of terms, we treat f as a child of APPLY_UF
+    assertEquals(t2.getNumChildren(), 2);
+    assertEquals(t2.getChild(0), f);
+    assertEquals(t2.getChild(1), two);
+    assertThrows(CVC5ApiException.class, () -> tnull.getChild(0));
+  }
+
+  @Test void getIntegerValue() throws CVC5ApiException
+  {
+    Term int1 = d_solver.mkInteger("-18446744073709551616");
+    Term int2 = d_solver.mkInteger("-18446744073709551615");
+    Term int3 = d_solver.mkInteger("-4294967296");
+    Term int4 = d_solver.mkInteger("-4294967295");
+    Term int5 = d_solver.mkInteger("-10");
+    Term int6 = d_solver.mkInteger("0");
+    Term int7 = d_solver.mkInteger("10");
+    Term int8 = d_solver.mkInteger("4294967295");
+    Term int9 = d_solver.mkInteger("4294967296");
+    Term int10 = d_solver.mkInteger("18446744073709551615");
+    Term int11 = d_solver.mkInteger("18446744073709551616");
+    Term int12 = d_solver.mkInteger("-0");
+
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(""));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-1-"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("0.0"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-0.1"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("012"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("0000"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-01"));
+    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-00"));
+
+    assertTrue(int1.isIntegerValue());
+    assertEquals(int1.getIntegerValue().toString(), "-18446744073709551616");
+    assertTrue(int2.isIntegerValue());
+    assertEquals(int2.getIntegerValue().toString(), "-18446744073709551615");
+    assertTrue(int3.isIntegerValue());
+    assertEquals(int3.getIntegerValue().longValue(), -4294967296L);
+    assertEquals(int3.getIntegerValue().toString(), "-4294967296");
+    assertTrue(int4.isIntegerValue());
+    assertEquals(int4.getIntegerValue().longValue(), -4294967295L);
+    assertEquals(int4.getIntegerValue().toString(), "-4294967295");
+    assertTrue(int5.isIntegerValue());
+    assertEquals(int5.getIntegerValue().intValue(), -10);
+    assertEquals(int5.getIntegerValue().intValue(), -10);
+    assertEquals(int5.getIntegerValue().toString(), "-10");
+    assertTrue(int6.isIntegerValue());
+    assertEquals(int6.getIntegerValue().intValue(), 0);
+    assertEquals(int6.getIntegerValue().intValue(), 0);
+    assertEquals(int6.getIntegerValue().toString(), "0");
+    assertTrue(int7.isIntegerValue());
+    assertEquals(int7.getIntegerValue().intValue(), 10);
+    assertEquals(int7.getIntegerValue().intValue(), 10);
+    assertEquals(int7.getIntegerValue().toString(), "10");
+    assertTrue(int8.isIntegerValue());
+    assertEquals(int8.getIntegerValue().longValue(), 4294967295L);
+    assertEquals(int8.getIntegerValue().toString(), "4294967295");
+    assertTrue(int9.isIntegerValue());
+    assertEquals(int9.getIntegerValue().longValue(), 4294967296L);
+    assertEquals(int9.getIntegerValue().toString(), "4294967296");
+    assertTrue(int10.isIntegerValue());
+
+    assertEquals(int10.getIntegerValue().toString(), "18446744073709551615");
+    assertTrue(int11.isIntegerValue());
+    assertEquals(int11.getIntegerValue().toString(), "18446744073709551616");
+  }
+
+  @Test void getString()
+  {
+    Term s1 = d_solver.mkString("abcde");
+    assertTrue(s1.isStringValue());
+    assertEquals(s1.getStringValue(), "abcde");
+  }
+
+  @Test void getReal() throws CVC5ApiException
+  {
+    Term real1 = d_solver.mkReal("0");
+    Term real2 = d_solver.mkReal(".0");
+    Term real3 = d_solver.mkReal("-17");
+    Term real4 = d_solver.mkReal("-3/5");
+    Term real5 = d_solver.mkReal("12.7");
+    Term real6 = d_solver.mkReal("1/4294967297");
+    Term real7 = d_solver.mkReal("4294967297");
+    Term real8 = d_solver.mkReal("1/18446744073709551617");
+    Term real9 = d_solver.mkReal("18446744073709551617");
+    Term real10 = d_solver.mkReal("2343.2343");
+
+    assertTrue(real1.isRealValue());
+    assertTrue(real2.isRealValue());
+    assertTrue(real3.isRealValue());
+    assertTrue(real4.isRealValue());
+    assertTrue(real5.isRealValue());
+    assertTrue(real6.isRealValue());
+    assertTrue(real7.isRealValue());
+    assertTrue(real8.isRealValue());
+    assertTrue(real9.isRealValue());
+    assertTrue(real10.isRealValue());
+
+    assertEquals("0/1", Utils.getRational(real1.getRealValue()));
+    assertEquals("0/1", Utils.getRational(real2.getRealValue()));
+    assertEquals("-17/1", Utils.getRational(real3.getRealValue()));
+    assertEquals("-3/5", Utils.getRational(real4.getRealValue()));
+    assertEquals("127/10", Utils.getRational(real5.getRealValue()));
+    assertEquals("1/4294967297", Utils.getRational(real6.getRealValue()));
+    assertEquals("4294967297/1", Utils.getRational(real7.getRealValue()));
+    assertEquals("1/18446744073709551617", Utils.getRational(real8.getRealValue()));
+    assertEquals("18446744073709551617/1", Utils.getRational(real9.getRealValue()));
+    assertEquals("23432343/10000", Utils.getRational(real10.getRealValue()));
+  }
+
+  @Test void getConstArrayBase()
+  {
+    Sort intsort = d_solver.getIntegerSort();
+    Sort arrsort = d_solver.mkArraySort(intsort, intsort);
+    Term one = d_solver.mkInteger(1);
+    Term constarr = d_solver.mkConstArray(arrsort, one);
+
+    assertTrue(constarr.isConstArray());
+    assertEquals(one, constarr.getConstArrayBase());
+  }
+
+  @Test void getBoolean()
+  {
+    Term b1 = d_solver.mkBoolean(true);
+    Term b2 = d_solver.mkBoolean(false);
+
+    assertTrue(b1.isBooleanValue());
+    assertTrue(b2.isBooleanValue());
+    assertTrue(b1.getBooleanValue());
+    assertFalse(b2.getBooleanValue());
+  }
+
+  @Test void getBitVector() throws CVC5ApiException
+  {
+    Term b1 = d_solver.mkBitVector(8, 15);
+    Term b2 = d_solver.mkBitVector(8, "00001111", 2);
+    Term b3 = d_solver.mkBitVector(8, "15", 10);
+    Term b4 = d_solver.mkBitVector(8, "0f", 16);
+    Term b5 = d_solver.mkBitVector(9, "00001111", 2);
+    Term b6 = d_solver.mkBitVector(9, "15", 10);
+    Term b7 = d_solver.mkBitVector(9, "0f", 16);
+
+    assertTrue(b1.isBitVectorValue());
+    assertTrue(b2.isBitVectorValue());
+    assertTrue(b3.isBitVectorValue());
+    assertTrue(b4.isBitVectorValue());
+    assertTrue(b5.isBitVectorValue());
+    assertTrue(b6.isBitVectorValue());
+    assertTrue(b7.isBitVectorValue());
+
+    assertEquals("00001111", b1.getBitVectorValue(2));
+    assertEquals("15", b1.getBitVectorValue(10));
+    assertEquals("f", b1.getBitVectorValue(16));
+    assertEquals("00001111", b2.getBitVectorValue(2));
+    assertEquals("15", b2.getBitVectorValue(10));
+    assertEquals("f", b2.getBitVectorValue(16));
+    assertEquals("00001111", b3.getBitVectorValue(2));
+    assertEquals("15", b3.getBitVectorValue(10));
+    assertEquals("f", b3.getBitVectorValue(16));
+    assertEquals("00001111", b4.getBitVectorValue(2));
+    assertEquals("15", b4.getBitVectorValue(10));
+    assertEquals("f", b4.getBitVectorValue(16));
+    assertEquals("000001111", b5.getBitVectorValue(2));
+    assertEquals("15", b5.getBitVectorValue(10));
+    assertEquals("f", b5.getBitVectorValue(16));
+    assertEquals("000001111", b6.getBitVectorValue(2));
+    assertEquals("15", b6.getBitVectorValue(10));
+    assertEquals("f", b6.getBitVectorValue(16));
+    assertEquals("000001111", b7.getBitVectorValue(2));
+    assertEquals("15", b7.getBitVectorValue(10));
+    assertEquals("f", b7.getBitVectorValue(16));
+  }
+
+  @Test void getAbstractValue() throws CVC5ApiException
+  {
+    Term v1 = d_solver.mkAbstractValue(1);
+    Term v2 = d_solver.mkAbstractValue("15");
+    Term v3 = d_solver.mkAbstractValue("18446744073709551617");
+
+    assertTrue(v1.isAbstractValue());
+    assertTrue(v2.isAbstractValue());
+    assertTrue(v3.isAbstractValue());
+    assertEquals("1", v1.getAbstractValue());
+    assertEquals("15", v2.getAbstractValue());
+    assertEquals("18446744073709551617", v3.getAbstractValue());
+  }
+
+  @Test void getTuple()
+  {
+    Sort s1 = d_solver.getIntegerSort();
+    Sort s2 = d_solver.getRealSort();
+    Sort s3 = d_solver.getStringSort();
+
+    Term t1 = d_solver.mkInteger(15);
+    Term t2 = d_solver.mkReal(17, 25);
+    Term t3 = d_solver.mkString("abc");
+
+    Term tup = d_solver.mkTuple(new Sort[] {s1, s2, s3}, new Term[] {t1, t2, t3});
+
+    assertTrue(tup.isTupleValue());
+    assertEquals(Arrays.asList((new Term[] {t1, t2, t3})), Arrays.asList(tup.getTupleValue()));
+  }
+
+  @Test void getFloatingPoint() throws CVC5ApiException
+  {
+    Term bvval = d_solver.mkBitVector(16, "0000110000000011", 2);
+    Term fp = d_solver.mkFloatingPoint(5, 11, bvval);
+
+    assertTrue(fp.isFloatingPointValue());
+    assertFalse(fp.isFloatingPointPosZero());
+    assertFalse(fp.isFloatingPointNegZero());
+    assertFalse(fp.isFloatingPointPosInf());
+    assertFalse(fp.isFloatingPointNegInf());
+    assertFalse(fp.isFloatingPointNaN());
+    assertEquals(new Triplet<Long, Long, Term>(5L, 11L, bvval), fp.getFloatingPointValue());
+
+    assertTrue(d_solver.mkPosZero(5, 11).isFloatingPointPosZero());
+    assertTrue(d_solver.mkNegZero(5, 11).isFloatingPointNegZero());
+    assertTrue(d_solver.mkPosInf(5, 11).isFloatingPointPosInf());
+    assertTrue(d_solver.mkNegInf(5, 11).isFloatingPointNegInf());
+    assertTrue(d_solver.mkNaN(5, 11).isFloatingPointNaN());
+  }
+
+  @Test void getSet()
+  {
+    Sort s = d_solver.mkSetSort(d_solver.getIntegerSort());
+
+    Term i1 = d_solver.mkInteger(5);
+    Term i2 = d_solver.mkInteger(7);
+
+    Term s1 = d_solver.mkEmptySet(s);
+    Term s2 = d_solver.mkTerm(Kind.SINGLETON, i1);
+    Term s3 = d_solver.mkTerm(Kind.SINGLETON, i1);
+    Term s4 = d_solver.mkTerm(Kind.SINGLETON, i2);
+    Term s5 = d_solver.mkTerm(Kind.UNION, s2, d_solver.mkTerm(Kind.UNION, s3, s4));
+
+    assertTrue(s1.isSetValue());
+    assertTrue(s2.isSetValue());
+    assertTrue(s3.isSetValue());
+    assertTrue(s4.isSetValue());
+    assertFalse(s5.isSetValue());
+    s5 = d_solver.simplify(s5);
+    assertTrue(s5.isSetValue());
+
+    assertSetsEquality(new Term[] {}, s1.getSetValue());
+    assertSetsEquality(new Term[] {i1}, s2.getSetValue());
+    assertSetsEquality(new Term[] {i1}, s3.getSetValue());
+    assertSetsEquality(new Term[] {i2}, s4.getSetValue());
+    assertSetsEquality(new Term[] {i1, i2}, s5.getSetValue());
+  }
+
+  private void assertSetsEquality(Term[] A, Set<Term> B)
+  {
+    List<Term> a = Arrays.stream(A).sorted().collect(Collectors.toList());
+    List<Term> b = B.stream().sorted().collect(Collectors.toList());
+    assertEquals(a, b);
+  }
+
+  @Test void getSequence()
+  {
+    Sort s = d_solver.mkSequenceSort(d_solver.getIntegerSort());
+
+    Term i1 = d_solver.mkInteger(5);
+    Term i2 = d_solver.mkInteger(7);
+
+    Term s1 = d_solver.mkEmptySequence(s);
+    Term s2 = d_solver.mkTerm(Kind.SEQ_UNIT, i1);
+    Term s3 = d_solver.mkTerm(Kind.SEQ_UNIT, i1);
+    Term s4 = d_solver.mkTerm(Kind.SEQ_UNIT, i2);
+    Term s5 = d_solver.mkTerm(Kind.SEQ_CONCAT, s2, d_solver.mkTerm(Kind.SEQ_CONCAT, s3, s4));
+
+    assertTrue(s1.isSequenceValue());
+    assertTrue(!s2.isSequenceValue());
+    assertTrue(!s3.isSequenceValue());
+    assertTrue(!s4.isSequenceValue());
+    assertTrue(!s5.isSequenceValue());
+
+    s2 = d_solver.simplify(s2);
+    s3 = d_solver.simplify(s3);
+    s4 = d_solver.simplify(s4);
+    s5 = d_solver.simplify(s5);
+
+    assertEquals(Arrays.asList(new Term[] {}), Arrays.asList(s1.getSequenceValue()));
+    assertEquals(Arrays.asList(new Term[] {i1}), Arrays.asList(s2.getSequenceValue()));
+    assertEquals(Arrays.asList(new Term[] {i1}), Arrays.asList(s3.getSequenceValue()));
+    assertEquals(Arrays.asList(new Term[] {i2}), Arrays.asList(s4.getSequenceValue()));
+    assertEquals(Arrays.asList(new Term[] {i1, i1, i2}), Arrays.asList(s5.getSequenceValue()));
+  }
+
+  @Test void getUninterpretedConst() throws CVC5ApiException
+  {
+    Sort s = d_solver.mkUninterpretedSort("test");
+    Term t1 = d_solver.mkUninterpretedConst(s, 3);
+    Term t2 = d_solver.mkUninterpretedConst(s, 5);
+
+    assertTrue(t1.isUninterpretedValue());
+    assertTrue(t2.isUninterpretedValue());
+
+    assertEquals(new Pair<Sort, Integer>(s, 3), t1.getUninterpretedValue());
+    assertEquals(new Pair<Sort, Integer>(s, 5), t2.getUninterpretedValue());
+  }
+
+  @Test void substitute()
+  {
+    Term x = d_solver.mkConst(d_solver.getIntegerSort(), "x");
+    Term one = d_solver.mkInteger(1);
+    Term ttrue = d_solver.mkTrue();
+    Term xpx = d_solver.mkTerm(PLUS, x, x);
+    Term onepone = d_solver.mkTerm(PLUS, one, one);
+
+    assertEquals(xpx.substitute(x, one), onepone);
+    assertEquals(onepone.substitute(one, x), xpx);
+    // incorrect due to type
+    assertThrows(CVC5ApiException.class, () -> xpx.substitute(one, ttrue));
+
+    // simultaneous substitution
+    Term y = d_solver.mkConst(d_solver.getIntegerSort(), "y");
+    Term xpy = d_solver.mkTerm(PLUS, x, y);
+    Term xpone = d_solver.mkTerm(PLUS, y, one);
+    List<Term> es = new ArrayList<>();
+    List<Term> rs = new ArrayList<>();
+    es.add(x);
+    rs.add(y);
+    es.add(y);
+    rs.add(one);
+    assertEquals(xpy.substitute(es, rs), xpone);
+
+    // incorrect substitution due to arity
+    rs.remove(rs.size() - 1);
+    assertThrows(CVC5ApiException.class, () -> xpy.substitute(es, rs));
+
+    // incorrect substitution due to types
+    rs.add(ttrue);
+    assertThrows(CVC5ApiException.class, () -> xpy.substitute(es, rs));
+
+    // null cannot substitute
+    Term tnull = d_solver.getNullTerm();
+    assertThrows(CVC5ApiException.class, () -> tnull.substitute(one, x));
+    assertThrows(CVC5ApiException.class, () -> xpx.substitute(tnull, x));
+    assertThrows(CVC5ApiException.class, () -> xpx.substitute(x, tnull));
+    rs.remove(rs.size() - 1);
+    rs.add(tnull);
+    assertThrows(CVC5ApiException.class, () -> xpy.substitute(es, rs));
+    es.clear();
+    rs.clear();
+    es.add(x);
+    rs.add(y);
+    assertThrows(CVC5ApiException.class, () -> tnull.substitute(es, rs));
+    es.add(tnull);
+    rs.add(one);
+    assertThrows(CVC5ApiException.class, () -> xpx.substitute(es, rs));
+  }
+
+  @Test void constArray() throws CVC5ApiException
+  {
+    Sort intsort = d_solver.getIntegerSort();
+    Sort arrsort = d_solver.mkArraySort(intsort, intsort);
+    Term a = d_solver.mkConst(arrsort, "a");
+    Term one = d_solver.mkInteger(1);
+    Term constarr = d_solver.mkConstArray(arrsort, one);
+
+    assertEquals(constarr.getKind(), CONST_ARRAY);
+    assertEquals(constarr.getConstArrayBase(), one);
+    assertThrows(CVC5ApiException.class, () -> a.getConstArrayBase());
+
+    arrsort = d_solver.mkArraySort(d_solver.getRealSort(), d_solver.getRealSort());
+    Term zero_array = d_solver.mkConstArray(arrsort, d_solver.mkReal(0));
+    Term stores = d_solver.mkTerm(STORE, zero_array, d_solver.mkReal(1), d_solver.mkReal(2));
+    stores = d_solver.mkTerm(STORE, stores, d_solver.mkReal(2), d_solver.mkReal(3));
+    stores = d_solver.mkTerm(STORE, stores, d_solver.mkReal(4), d_solver.mkReal(5));
+  }
+
+  @Test void getSequenceValue() throws CVC5ApiException
+  {
+    Sort realsort = d_solver.getRealSort();
+    Sort seqsort = d_solver.mkSequenceSort(realsort);
+    Term s = d_solver.mkEmptySequence(seqsort);
+
+    assertEquals(s.getKind(), CONST_SEQUENCE);
+    // empty sequence has zero elements
+    Term[] cs = s.getSequenceValue();
+    assertTrue(cs.length == 0);
+
+    // A seq.unit app is not a constant sequence (regardless of whether it is
+    // applied to a constant).
+    Term su = d_solver.mkTerm(SEQ_UNIT, d_solver.mkReal(1));
+    assertThrows(CVC5ApiException.class, () -> su.getSequenceValue());
+  }
+
+  @Test void termScopedToString()
+  {
+    Sort intsort = d_solver.getIntegerSort();
+    Term x = d_solver.mkConst(intsort, "x");
+    assertEquals(x.toString(), "x");
+    Solver solver2;
+    assertEquals(x.toString(), "x");
+  }
+}
diff --git a/test/unit/api/java/cvc5/DatatypeTest.java b/test/unit/api/java/cvc5/DatatypeTest.java
deleted file mode 100644 (file)
index 2f57b6a..0000000
+++ /dev/null
@@ -1,566 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Andrew Reynolds, Aina Niemetz, Andres Noetzli, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the datatype classes of the Java API.
- */
-
-package cvc5;
-
-import static cvc5.Kind.*;
-import static org.junit.jupiter.api.Assertions.*;
-
-import java.util.*;
-import java.util.concurrent.atomic.AtomicReference;
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
-
-class DatatypeTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  @Test void mkDatatypeSort() throws CVC5ApiException
-  {
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    Sort listSort = d_solver.mkDatatypeSort(dtypeSpec);
-    Datatype d = listSort.getDatatype();
-    DatatypeConstructor consConstr = d.getConstructor(0);
-    DatatypeConstructor nilConstr = d.getConstructor(1);
-    assertThrows(CVC5ApiException.class, () -> d.getConstructor(2));
-    assertDoesNotThrow(() -> consConstr.getConstructorTerm());
-    assertDoesNotThrow(() -> nilConstr.getConstructorTerm());
-  }
-
-  @Test void mkDatatypeSorts()
-  {
-    /* Create two mutual datatypes corresponding to this definition
-     * block:
-     *
-     *   DATATYPE
-     *     tree = node(left: tree, right: tree) | leaf(data: list),
-     *     list = cons(car: tree, cdr: list) | nil
-     *   END;
-     */
-    // Make unresolved types as placeholders
-    Set<Sort> unresTypes = new HashSet<>();
-    Sort unresTree = d_solver.mkUninterpretedSort("tree");
-    Sort unresList = d_solver.mkUninterpretedSort("list");
-    unresTypes.add(unresTree);
-    unresTypes.add(unresList);
-
-    DatatypeDecl tree = d_solver.mkDatatypeDecl("tree");
-    DatatypeConstructorDecl node = d_solver.mkDatatypeConstructorDecl("node");
-    node.addSelector("left", unresTree);
-    node.addSelector("right", unresTree);
-    tree.addConstructor(node);
-
-    DatatypeConstructorDecl leaf = d_solver.mkDatatypeConstructorDecl("leaf");
-    leaf.addSelector("data", unresList);
-    tree.addConstructor(leaf);
-
-    DatatypeDecl list = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("car", unresTree);
-    cons.addSelector("cdr", unresTree);
-    list.addConstructor(cons);
-
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    list.addConstructor(nil);
-
-    List<DatatypeDecl> dtdecls = new ArrayList<>();
-    dtdecls.add(tree);
-    dtdecls.add(list);
-
-    AtomicReference<List<Sort>> atomic = new AtomicReference<>();
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    List<Sort> dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), dtdecls.size());
-    for (int i = 0, ndecl = dtdecls.size(); i < ndecl; i++)
-    {
-      assertTrue(dtsorts.get(i).isDatatype());
-      assertFalse(dtsorts.get(i).getDatatype().isFinite());
-      assertEquals(dtsorts.get(i).getDatatype().getName(), dtdecls.get(i).getName());
-    }
-    // verify the resolution was correct
-    Datatype dtTree = dtsorts.get(0).getDatatype();
-    DatatypeConstructor dtcTreeNode = dtTree.getConstructor(0);
-    assertEquals(dtcTreeNode.getName(), "node");
-    DatatypeSelector dtsTreeNodeLeft = dtcTreeNode.getSelector(0);
-    assertEquals(dtsTreeNodeLeft.getName(), "left");
-    // argument type should have resolved to be recursive
-    assertTrue(dtsTreeNodeLeft.getRangeSort().isDatatype());
-    assertEquals(dtsTreeNodeLeft.getRangeSort(), dtsorts.get(0));
-
-    // fails due to empty datatype
-    List<DatatypeDecl> dtdeclsBad = new ArrayList<>();
-    DatatypeDecl emptyD = d_solver.mkDatatypeDecl("emptyD");
-    dtdeclsBad.add(emptyD);
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkDatatypeSorts(dtdeclsBad));
-  }
-
-  @Test void datatypeStructs() throws CVC5ApiException
-  {
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-
-    // create datatype sort to test
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", intSort);
-    cons.addSelectorSelf("tail");
-    Sort nullSort = d_solver.getNullSort();
-    assertThrows(CVC5ApiException.class, () -> cons.addSelector("null", nullSort));
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
-    Datatype dt = dtypeSort.getDatatype();
-    assertFalse(dt.isCodatatype());
-    assertFalse(dt.isTuple());
-    assertFalse(dt.isRecord());
-    assertFalse(dt.isFinite());
-    assertTrue(dt.isWellFounded());
-    // get constructor
-    DatatypeConstructor dcons = dt.getConstructor(0);
-    Term consTerm = dcons.getConstructorTerm();
-    assertEquals(dcons.getNumSelectors(), 2);
-
-    // create datatype sort to test
-    DatatypeDecl dtypeSpecEnum = d_solver.mkDatatypeDecl("enum");
-    DatatypeConstructorDecl ca = d_solver.mkDatatypeConstructorDecl("A");
-    dtypeSpecEnum.addConstructor(ca);
-    DatatypeConstructorDecl cb = d_solver.mkDatatypeConstructorDecl("B");
-    dtypeSpecEnum.addConstructor(cb);
-    DatatypeConstructorDecl cc = d_solver.mkDatatypeConstructorDecl("C");
-    dtypeSpecEnum.addConstructor(cc);
-    Sort dtypeSortEnum = d_solver.mkDatatypeSort(dtypeSpecEnum);
-    Datatype dtEnum = dtypeSortEnum.getDatatype();
-    assertFalse(dtEnum.isTuple());
-    assertTrue(dtEnum.isFinite());
-
-    // create codatatype
-    DatatypeDecl dtypeSpecStream = d_solver.mkDatatypeDecl("stream", true);
-    DatatypeConstructorDecl consStream = d_solver.mkDatatypeConstructorDecl("cons");
-    consStream.addSelector("head", intSort);
-    consStream.addSelectorSelf("tail");
-    dtypeSpecStream.addConstructor(consStream);
-    Sort dtypeSortStream = d_solver.mkDatatypeSort(dtypeSpecStream);
-    Datatype dtStream = dtypeSortStream.getDatatype();
-    assertTrue(dtStream.isCodatatype());
-    assertFalse(dtStream.isFinite());
-    // codatatypes may be well-founded
-    assertTrue(dtStream.isWellFounded());
-
-    // create tuple
-    Sort tupSort = d_solver.mkTupleSort(new Sort[] {boolSort});
-    Datatype dtTuple = tupSort.getDatatype();
-    assertTrue(dtTuple.isTuple());
-    assertFalse(dtTuple.isRecord());
-    assertTrue(dtTuple.isFinite());
-    assertTrue(dtTuple.isWellFounded());
-
-    // create record
-    Pair<String, Sort>[] fields = new Pair[] {new Pair<>("b", boolSort), new Pair<>("i", intSort)};
-    Sort recSort = d_solver.mkRecordSort(fields);
-    assertTrue(recSort.isDatatype());
-    Datatype dtRecord = recSort.getDatatype();
-    assertFalse(dtRecord.isTuple());
-    assertTrue(dtRecord.isRecord());
-    assertFalse(dtRecord.isFinite());
-    assertTrue(dtRecord.isWellFounded());
-  }
-
-  @Test void datatypeNames() throws CVC5ApiException
-  {
-    Sort intSort = d_solver.getIntegerSort();
-
-    // create datatype sort to test
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    assertDoesNotThrow(() -> dtypeSpec.getName());
-    assertEquals(dtypeSpec.getName(), "list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", intSort);
-    cons.addSelectorSelf("tail");
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
-    Datatype dt = dtypeSort.getDatatype();
-    assertEquals(dt.getName(), "list");
-    assertDoesNotThrow(() -> dt.getConstructor("nil"));
-    assertDoesNotThrow(() -> dt.getConstructor("cons"));
-    assertThrows(CVC5ApiException.class, () -> dt.getConstructor("head"));
-    assertThrows(CVC5ApiException.class, () -> dt.getConstructor(""));
-
-    DatatypeConstructor dcons = dt.getConstructor(0);
-    assertEquals(dcons.getName(), "cons");
-    assertDoesNotThrow(() -> dcons.getSelector("head"));
-    assertDoesNotThrow(() -> dcons.getSelector("tail"));
-    assertThrows(CVC5ApiException.class, () -> dcons.getSelector("cons"));
-
-    // get selector
-    DatatypeSelector dselTail = dcons.getSelector(1);
-    assertEquals(dselTail.getName(), "tail");
-    assertEquals(dselTail.getRangeSort(), dtypeSort);
-
-    // possible to construct null datatype declarations if not using solver
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullDatatypeDecl().getName());
-  }
-
-  @Test void parametricDatatype() throws CVC5ApiException
-  {
-    List<Sort> v = new ArrayList<>();
-    Sort t1 = d_solver.mkParamSort("T1");
-    Sort t2 = d_solver.mkParamSort("T2");
-    v.add(t1);
-    v.add(t2);
-    DatatypeDecl pairSpec = d_solver.mkDatatypeDecl("pair", v);
-
-    DatatypeConstructorDecl mkpair = d_solver.mkDatatypeConstructorDecl("mk-pair");
-    mkpair.addSelector("first", t1);
-    mkpair.addSelector("second", t2);
-    pairSpec.addConstructor(mkpair);
-
-    Sort pairType = d_solver.mkDatatypeSort(pairSpec);
-
-    assertTrue(pairType.getDatatype().isParametric());
-
-    v.clear();
-    v.add(d_solver.getIntegerSort());
-    v.add(d_solver.getIntegerSort());
-    Sort pairIntInt = pairType.instantiate(v);
-    v.clear();
-    v.add(d_solver.getRealSort());
-    v.add(d_solver.getRealSort());
-    Sort pairRealReal = pairType.instantiate(v);
-    v.clear();
-    v.add(d_solver.getRealSort());
-    v.add(d_solver.getIntegerSort());
-    Sort pairRealInt = pairType.instantiate(v);
-    v.clear();
-    v.add(d_solver.getIntegerSort());
-    v.add(d_solver.getRealSort());
-    Sort pairIntReal = pairType.instantiate(v);
-
-    assertNotEquals(pairIntInt, pairRealReal);
-    assertNotEquals(pairIntReal, pairRealReal);
-    assertNotEquals(pairRealInt, pairRealReal);
-    assertNotEquals(pairIntInt, pairIntReal);
-    assertNotEquals(pairIntInt, pairRealInt);
-    assertNotEquals(pairIntReal, pairRealInt);
-
-    assertTrue(pairRealReal.isComparableTo(pairRealReal));
-    assertFalse(pairIntReal.isComparableTo(pairRealReal));
-    assertFalse(pairRealInt.isComparableTo(pairRealReal));
-    assertFalse(pairIntInt.isComparableTo(pairRealReal));
-    assertFalse(pairRealReal.isComparableTo(pairRealInt));
-    assertFalse(pairIntReal.isComparableTo(pairRealInt));
-    assertTrue(pairRealInt.isComparableTo(pairRealInt));
-    assertFalse(pairIntInt.isComparableTo(pairRealInt));
-    assertFalse(pairRealReal.isComparableTo(pairIntReal));
-    assertTrue(pairIntReal.isComparableTo(pairIntReal));
-    assertFalse(pairRealInt.isComparableTo(pairIntReal));
-    assertFalse(pairIntInt.isComparableTo(pairIntReal));
-    assertFalse(pairRealReal.isComparableTo(pairIntInt));
-    assertFalse(pairIntReal.isComparableTo(pairIntInt));
-    assertFalse(pairRealInt.isComparableTo(pairIntInt));
-    assertTrue(pairIntInt.isComparableTo(pairIntInt));
-
-    assertTrue(pairRealReal.isSubsortOf(pairRealReal));
-    assertFalse(pairIntReal.isSubsortOf(pairRealReal));
-    assertFalse(pairRealInt.isSubsortOf(pairRealReal));
-    assertFalse(pairIntInt.isSubsortOf(pairRealReal));
-    assertFalse(pairRealReal.isSubsortOf(pairRealInt));
-    assertFalse(pairIntReal.isSubsortOf(pairRealInt));
-    assertTrue(pairRealInt.isSubsortOf(pairRealInt));
-    assertFalse(pairIntInt.isSubsortOf(pairRealInt));
-    assertFalse(pairRealReal.isSubsortOf(pairIntReal));
-    assertTrue(pairIntReal.isSubsortOf(pairIntReal));
-    assertFalse(pairRealInt.isSubsortOf(pairIntReal));
-    assertFalse(pairIntInt.isSubsortOf(pairIntReal));
-    assertFalse(pairRealReal.isSubsortOf(pairIntInt));
-    assertFalse(pairIntReal.isSubsortOf(pairIntInt));
-    assertFalse(pairRealInt.isSubsortOf(pairIntInt));
-    assertTrue(pairIntInt.isSubsortOf(pairIntInt));
-  }
-
-  @Test void datatypeSimplyRec() throws CVC5ApiException
-  {
-    /* Create mutual datatypes corresponding to this definition block:
-     *
-     *   DATATYPE
-     *     wlist = leaf(data: list),
-     *     list = cons(car: wlist, cdr: list) | nil,
-     *     ns = elem(ndata: set(wlist)) | elemArray(ndata2: array(list, list))
-     *   END;
-     */
-    // Make unresolved types as placeholders
-    Set<Sort> unresTypes = new HashSet<>();
-    Sort unresWList = d_solver.mkUninterpretedSort("wlist");
-    Sort unresList = d_solver.mkUninterpretedSort("list");
-    Sort unresNs = d_solver.mkUninterpretedSort("ns");
-    unresTypes.add(unresWList);
-    unresTypes.add(unresList);
-    unresTypes.add(unresNs);
-
-    DatatypeDecl wlist = d_solver.mkDatatypeDecl("wlist");
-    DatatypeConstructorDecl leaf = d_solver.mkDatatypeConstructorDecl("leaf");
-    leaf.addSelector("data", unresList);
-    wlist.addConstructor(leaf);
-
-    DatatypeDecl list = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("car", unresWList);
-    cons.addSelector("cdr", unresList);
-    list.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    list.addConstructor(nil);
-
-    DatatypeDecl ns = d_solver.mkDatatypeDecl("ns");
-    DatatypeConstructorDecl elem = d_solver.mkDatatypeConstructorDecl("elem");
-    elem.addSelector("ndata", d_solver.mkSetSort(unresWList));
-    ns.addConstructor(elem);
-    DatatypeConstructorDecl elemArray = d_solver.mkDatatypeConstructorDecl("elemArray");
-    elemArray.addSelector("ndata", d_solver.mkArraySort(unresList, unresList));
-    ns.addConstructor(elemArray);
-
-    List<DatatypeDecl> dtdecls = new ArrayList<>();
-    dtdecls.add(wlist);
-    dtdecls.add(list);
-    dtdecls.add(ns);
-    // this is well-founded and has no nested recursion
-    AtomicReference<List<Sort>> atomic = new AtomicReference<>();
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    List<Sort> dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), 3);
-    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(1).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(2).getDatatype().isWellFounded());
-    assertFalse(dtsorts.get(0).getDatatype().hasNestedRecursion());
-    assertFalse(dtsorts.get(1).getDatatype().hasNestedRecursion());
-    assertFalse(dtsorts.get(2).getDatatype().hasNestedRecursion());
-
-    /* Create mutual datatypes corresponding to this definition block:
-     *   DATATYPE
-     *     ns2 = elem2(ndata: array(int,ns2)) | nil2
-     *   END;
-     */
-    unresTypes.clear();
-    Sort unresNs2 = d_solver.mkUninterpretedSort("ns2");
-    unresTypes.add(unresNs2);
-
-    DatatypeDecl ns2 = d_solver.mkDatatypeDecl("ns2");
-    DatatypeConstructorDecl elem2 = d_solver.mkDatatypeConstructorDecl("elem2");
-    elem2.addSelector("ndata", d_solver.mkArraySort(d_solver.getIntegerSort(), unresNs2));
-    ns2.addConstructor(elem2);
-    DatatypeConstructorDecl nil2 = d_solver.mkDatatypeConstructorDecl("nil2");
-    ns2.addConstructor(nil2);
-
-    dtdecls.clear();
-    dtdecls.add(ns2);
-
-    // dtsorts.clear();
-    // this is not well-founded due to non-simple recursion
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), 1);
-    assertTrue(
-        dtsorts.get(0).getDatatype().getConstructor(0).getSelector(0).getRangeSort().isArray());
-    assertEquals(dtsorts.get(0)
-                     .getDatatype()
-                     .getConstructor(0)
-                     .getSelector(0)
-                     .getRangeSort()
-                     .getArrayElementSort(),
-        dtsorts.get(0));
-    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
-
-    /* Create mutual datatypes corresponding to this definition block:
-     *   DATATYPE
-     *     list3 = cons3(car: ns3, cdr: list3) | nil3,
-     *     ns3 = elem3(ndata: set(list3))
-     *   END;
-     */
-    unresTypes.clear();
-    Sort unresNs3 = d_solver.mkUninterpretedSort("ns3");
-    unresTypes.add(unresNs3);
-    Sort unresList3 = d_solver.mkUninterpretedSort("list3");
-    unresTypes.add(unresList3);
-
-    DatatypeDecl list3 = d_solver.mkDatatypeDecl("list3");
-    DatatypeConstructorDecl cons3 = d_solver.mkDatatypeConstructorDecl("cons3");
-    cons3.addSelector("car", unresNs3);
-    cons3.addSelector("cdr", unresList3);
-    list3.addConstructor(cons3);
-    DatatypeConstructorDecl nil3 = d_solver.mkDatatypeConstructorDecl("nil3");
-    list3.addConstructor(nil3);
-
-    DatatypeDecl ns3 = d_solver.mkDatatypeDecl("ns3");
-    DatatypeConstructorDecl elem3 = d_solver.mkDatatypeConstructorDecl("elem3");
-    elem3.addSelector("ndata", d_solver.mkSetSort(unresList3));
-    ns3.addConstructor(elem3);
-
-    dtdecls.clear();
-    dtdecls.add(list3);
-    dtdecls.add(ns3);
-
-    // dtsorts.clear();
-    // both are well-founded and have nested recursion
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), 2);
-    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(1).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
-    assertTrue(dtsorts.get(1).getDatatype().hasNestedRecursion());
-
-    /* Create mutual datatypes corresponding to this definition block:
-     *   DATATYPE
-     *     list4 = cons(car: set(ns4), cdr: list4) | nil,
-     *     ns4 = elem(ndata: list4)
-     *   END;
-     */
-    unresTypes.clear();
-    Sort unresNs4 = d_solver.mkUninterpretedSort("ns4");
-    unresTypes.add(unresNs4);
-    Sort unresList4 = d_solver.mkUninterpretedSort("list4");
-    unresTypes.add(unresList4);
-
-    DatatypeDecl list4 = d_solver.mkDatatypeDecl("list4");
-    DatatypeConstructorDecl cons4 = d_solver.mkDatatypeConstructorDecl("cons4");
-    cons4.addSelector("car", d_solver.mkSetSort(unresNs4));
-    cons4.addSelector("cdr", unresList4);
-    list4.addConstructor(cons4);
-    DatatypeConstructorDecl nil4 = d_solver.mkDatatypeConstructorDecl("nil4");
-    list4.addConstructor(nil4);
-
-    DatatypeDecl ns4 = d_solver.mkDatatypeDecl("ns4");
-    DatatypeConstructorDecl elem4 = d_solver.mkDatatypeConstructorDecl("elem3");
-    elem4.addSelector("ndata", unresList4);
-    ns4.addConstructor(elem4);
-
-    dtdecls.clear();
-    dtdecls.add(list4);
-    dtdecls.add(ns4);
-
-    // dtsorts.clear();
-    // both are well-founded and have nested recursion
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), 2);
-    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(1).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
-    assertTrue(dtsorts.get(1).getDatatype().hasNestedRecursion());
-
-    /* Create mutual datatypes corresponding to this definition block:
-     *   DATATYPE
-     *     list5[X] = cons(car: X, cdr: list5[list5[X]]) | nil
-     *   END;
-     */
-    unresTypes.clear();
-    Sort unresList5 = d_solver.mkSortConstructorSort("list5", 1);
-    unresTypes.add(unresList5);
-
-    List<Sort> v = new ArrayList<>();
-    Sort x = d_solver.mkParamSort("X");
-    v.add(x);
-    DatatypeDecl list5 = d_solver.mkDatatypeDecl("list5", v);
-
-    List<Sort> args = new ArrayList<>();
-    args.add(x);
-    Sort urListX = unresList5.instantiate(args);
-    args.set(0, urListX);
-    Sort urListListX = unresList5.instantiate(args);
-
-    DatatypeConstructorDecl cons5 = d_solver.mkDatatypeConstructorDecl("cons5");
-    cons5.addSelector("car", x);
-    cons5.addSelector("cdr", urListListX);
-    list5.addConstructor(cons5);
-    DatatypeConstructorDecl nil5 = d_solver.mkDatatypeConstructorDecl("nil5");
-    list5.addConstructor(nil5);
-
-    dtdecls.clear();
-    dtdecls.add(list5);
-
-    // well-founded and has nested recursion
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), 1);
-    assertTrue(dtsorts.get(0).getDatatype().isWellFounded());
-    assertTrue(dtsorts.get(0).getDatatype().hasNestedRecursion());
-  }
-
-  @Test void datatypeSpecializedCons() throws CVC5ApiException
-  {
-    /* Create mutual datatypes corresponding to this definition block:
-     *   DATATYPE
-     *     plist[X] = pcons(car: X, cdr: plist[X]) | pnil
-     *   END;
-     */
-    // Make unresolved types as placeholders
-    Set<Sort> unresTypes = new HashSet<>();
-    Sort unresList = d_solver.mkSortConstructorSort("plist", 1);
-    unresTypes.add(unresList);
-
-    List<Sort> v = new ArrayList<>();
-    Sort x = d_solver.mkParamSort("X");
-    v.add(x);
-    DatatypeDecl plist = d_solver.mkDatatypeDecl("plist", v);
-
-    List<Sort> args = new ArrayList<>();
-    args.add(x);
-    Sort urListX = unresList.instantiate(args);
-
-    DatatypeConstructorDecl pcons = d_solver.mkDatatypeConstructorDecl("pcons");
-    pcons.addSelector("car", x);
-    pcons.addSelector("cdr", urListX);
-    plist.addConstructor(pcons);
-    DatatypeConstructorDecl nil5 = d_solver.mkDatatypeConstructorDecl("pnil");
-    plist.addConstructor(nil5);
-
-    List<DatatypeDecl> dtdecls = new ArrayList<>();
-    dtdecls.add(plist);
-
-    // make the datatype sorts
-    AtomicReference<List<Sort>> atomic = new AtomicReference<>();
-    assertDoesNotThrow(() -> atomic.set(d_solver.mkDatatypeSorts(dtdecls, unresTypes)));
-    List<Sort> dtsorts = atomic.get();
-    assertEquals(dtsorts.size(), 1);
-    Datatype d = dtsorts.get(0).getDatatype();
-    DatatypeConstructor nilc = d.getConstructor(0);
-
-    Sort isort = d_solver.getIntegerSort();
-    List<Sort> iargs = new ArrayList<>();
-    iargs.add(isort);
-    Sort listInt = dtsorts.get(0).instantiate(iargs);
-
-    AtomicReference<Term> atomicTerm = new AtomicReference<>();
-    // get the specialized constructor term for list[Int]
-    assertDoesNotThrow(() -> atomicTerm.set(nilc.getSpecializedConstructorTerm(listInt)));
-    Term testConsTerm = atomicTerm.get();
-    assertNotEquals(testConsTerm, nilc.getConstructorTerm());
-    // error to get the specialized constructor term for Int
-    assertThrows(CVC5ApiException.class, () -> nilc.getSpecializedConstructorTerm(isort));
-  }
-}
diff --git a/test/unit/api/java/cvc5/GrammarTest.java b/test/unit/api/java/cvc5/GrammarTest.java
deleted file mode 100644 (file)
index 6e7c6ce..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Abdalrhman Mohamed, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the guards of the Java API functions.
- */
-
-package cvc5;
-
-import static cvc5.Kind.*;
-import static org.junit.jupiter.api.Assertions.*;
-
-import java.util.Arrays;
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
-
-class GrammarTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  @Test void addRule()
-  {
-    Sort bool = d_solver.getBooleanSort();
-    Sort integer = d_solver.getIntegerSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term start = d_solver.mkVar(bool);
-    Term nts = d_solver.mkVar(bool);
-
-    Grammar g = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
-
-    assertDoesNotThrow(() -> g.addRule(start, d_solver.mkBoolean(false)));
-
-    assertThrows(CVC5ApiException.class, () -> g.addRule(nullTerm, d_solver.mkBoolean(false)));
-    assertThrows(CVC5ApiException.class, () -> g.addRule(start, nullTerm));
-    assertThrows(CVC5ApiException.class, () -> g.addRule(nts, d_solver.mkBoolean(false)));
-    assertThrows(CVC5ApiException.class, () -> g.addRule(start, d_solver.mkInteger(0)));
-    assertThrows(CVC5ApiException.class, () -> g.addRule(start, nts));
-
-    d_solver.synthFun("f", new Term[] {}, bool, g);
-
-    assertThrows(CVC5ApiException.class, () -> g.addRule(start, d_solver.mkBoolean(false)));
-  }
-
-  @Test void addRules()
-  {
-    Sort bool = d_solver.getBooleanSort();
-    Sort integer = d_solver.getIntegerSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term start = d_solver.mkVar(bool);
-    Term nts = d_solver.mkVar(bool);
-
-    Grammar g = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
-
-    assertDoesNotThrow(() -> g.addRules(start, new Term[] {d_solver.mkBoolean(false)}));
-
-    assertThrows(
-        CVC5ApiException.class, () -> g.addRules(nullTerm, new Term[] {d_solver.mkBoolean(false)}));
-    assertThrows(CVC5ApiException.class, () -> g.addRules(start, new Term[] {nullTerm}));
-    assertThrows(
-        CVC5ApiException.class, () -> g.addRules(nts, new Term[] {d_solver.mkBoolean(false)}));
-    assertThrows(
-        CVC5ApiException.class, () -> g.addRules(start, new Term[] {d_solver.mkInteger(0)}));
-    assertThrows(CVC5ApiException.class, () -> g.addRules(start, new Term[] {nts}));
-
-    d_solver.synthFun("f", new Term[] {}, bool, g);
-
-    assertThrows(
-        CVC5ApiException.class, () -> g.addRules(start, new Term[] {d_solver.mkBoolean(false)}));
-  }
-
-  @Test void addAnyConstant()
-  {
-    Sort bool = d_solver.getBooleanSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term start = d_solver.mkVar(bool);
-    Term nts = d_solver.mkVar(bool);
-
-    Grammar g = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
-
-    assertDoesNotThrow(() -> g.addAnyConstant(start));
-    assertDoesNotThrow(() -> g.addAnyConstant(start));
-
-    assertThrows(CVC5ApiException.class, () -> g.addAnyConstant(nullTerm));
-    assertThrows(CVC5ApiException.class, () -> g.addAnyConstant(nts));
-
-    d_solver.synthFun("f", new Term[] {}, bool, g);
-
-    assertThrows(CVC5ApiException.class, () -> g.addAnyConstant(start));
-  }
-
-  @Test void addAnyVariable()
-  {
-    Sort bool = d_solver.getBooleanSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term x = d_solver.mkVar(bool);
-    Term start = d_solver.mkVar(bool);
-    Term nts = d_solver.mkVar(bool);
-
-    Grammar g1 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start});
-    Grammar g2 = d_solver.mkSygusGrammar(new Term[] {}, new Term[] {start});
-
-    assertDoesNotThrow(() -> g1.addAnyVariable(start));
-    assertDoesNotThrow(() -> g1.addAnyVariable(start));
-    assertDoesNotThrow(() -> g2.addAnyVariable(start));
-
-    assertThrows(CVC5ApiException.class, () -> g1.addAnyVariable(nullTerm));
-    assertThrows(CVC5ApiException.class, () -> g1.addAnyVariable(nts));
-
-    d_solver.synthFun("f", new Term[] {}, bool, g1);
-
-    assertThrows(CVC5ApiException.class, () -> g1.addAnyVariable(start));
-  }
-}
diff --git a/test/unit/api/java/cvc5/OpTest.java b/test/unit/api/java/cvc5/OpTest.java
deleted file mode 100644 (file)
index f4dd181..0000000
+++ /dev/null
@@ -1,157 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Makai Mann, Aina Niemetz, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the Op class.
- */
-
-package cvc5;
-
-import static cvc5.Kind.*;
-import static org.junit.jupiter.api.Assertions.*;
-
-import java.util.Arrays;
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
-
-class OpTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  @Test void getKind() throws CVC5ApiException
-  {
-    Op x;
-    x = d_solver.mkOp(BITVECTOR_EXTRACT, 31, 1);
-    assertDoesNotThrow(() -> x.getKind());
-  }
-
-  @Test void isNull() throws CVC5ApiException
-  {
-    Op x = d_solver.getNullOp();
-    assertTrue(x.isNull());
-    x = d_solver.mkOp(BITVECTOR_EXTRACT, 31, 1);
-    assertFalse(x.isNull());
-  }
-
-  @Test void opFromKind()
-  {
-    assertDoesNotThrow(() -> d_solver.mkOp(PLUS));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT));
-  }
-
-  @Test void getIndicesString() throws CVC5ApiException
-  {
-    Op x = d_solver.getNullOp();
-    assertThrows(CVC5ApiException.class, () -> x.getStringIndices());
-
-    Op divisible_ot = d_solver.mkOp(DIVISIBLE, 4);
-    assertTrue(divisible_ot.isIndexed());
-    String divisible_idx = divisible_ot.getStringIndices()[0];
-    assertEquals(divisible_idx, "4");
-  }
-
-  @Test void getIndicesUint() throws CVC5ApiException
-  {
-    Op bitvector_repeat_ot = d_solver.mkOp(BITVECTOR_REPEAT, 5);
-    assertTrue(bitvector_repeat_ot.isIndexed());
-    int bitvector_repeat_idx = bitvector_repeat_ot.getIntegerIndices()[0];
-    assertEquals(bitvector_repeat_idx, 5);
-
-    // unlike bitvector_repeat_ot.getIndices<std::pair<uint32_t, uint32_t>>() in
-    // c++, this does not throw in Java
-    // assertThrows(CVC5ApiException.class,
-    //              () -> bitvector_repeat_ot.getIntegerIndices());
-
-    Op bitvector_zero_extend_ot = d_solver.mkOp(BITVECTOR_ZERO_EXTEND, 6);
-    int bitvector_zero_extend_idx = bitvector_zero_extend_ot.getIntegerIndices()[0];
-    assertEquals(bitvector_zero_extend_idx, 6);
-
-    Op bitvector_sign_extend_ot = d_solver.mkOp(BITVECTOR_SIGN_EXTEND, 7);
-    int bitvector_sign_extend_idx = bitvector_sign_extend_ot.getIntegerIndices()[0];
-    assertEquals(bitvector_sign_extend_idx, 7);
-
-    Op bitvector_rotate_left_ot = d_solver.mkOp(BITVECTOR_ROTATE_LEFT, 8);
-    int bitvector_rotate_left_idx = bitvector_rotate_left_ot.getIntegerIndices()[0];
-    assertEquals(bitvector_rotate_left_idx, 8);
-
-    Op bitvector_rotate_right_ot = d_solver.mkOp(BITVECTOR_ROTATE_RIGHT, 9);
-    int bitvector_rotate_right_idx = bitvector_rotate_right_ot.getIntegerIndices()[0];
-    assertEquals(bitvector_rotate_right_idx, 9);
-
-    Op int_to_bitvector_ot = d_solver.mkOp(INT_TO_BITVECTOR, 10);
-    int int_to_bitvector_idx = int_to_bitvector_ot.getIntegerIndices()[0];
-    assertEquals(int_to_bitvector_idx, 10);
-
-    Op floatingpoint_to_ubv_ot = d_solver.mkOp(FLOATINGPOINT_TO_UBV, 11);
-    int floatingpoint_to_ubv_idx = floatingpoint_to_ubv_ot.getIntegerIndices()[0];
-    assertEquals(floatingpoint_to_ubv_idx, 11);
-
-    Op floatingpoint_to_sbv_ot = d_solver.mkOp(FLOATINGPOINT_TO_SBV, 13);
-    int floatingpoint_to_sbv_idx = floatingpoint_to_sbv_ot.getIntegerIndices()[0];
-    assertEquals(floatingpoint_to_sbv_idx, 13);
-  }
-
-  @Test void getIndicesPairUint() throws CVC5ApiException
-  {
-    Op bitvector_extract_ot = d_solver.mkOp(BITVECTOR_EXTRACT, 4, 0);
-    assertTrue(bitvector_extract_ot.isIndexed());
-    int[] bitvector_extract_indices = bitvector_extract_ot.getIntegerIndices();
-    assertArrayEquals(bitvector_extract_indices, new int[] {4, 0});
-
-    Op floatingpoint_to_fp_ieee_bitvector_ot =
-        d_solver.mkOp(FLOATINGPOINT_TO_FP_IEEE_BITVECTOR, 4, 25);
-    int[] floatingpoint_to_fp_ieee_bitvector_indices =
-        floatingpoint_to_fp_ieee_bitvector_ot.getIntegerIndices();
-    assertArrayEquals(floatingpoint_to_fp_ieee_bitvector_indices, new int[] {4, 25});
-
-    Op floatingpoint_to_fp_floatingpoint_ot =
-        d_solver.mkOp(FLOATINGPOINT_TO_FP_FLOATINGPOINT, 4, 25);
-    int[] floatingpoint_to_fp_floatingpoint_indices =
-        floatingpoint_to_fp_floatingpoint_ot.getIntegerIndices();
-    assertArrayEquals(floatingpoint_to_fp_floatingpoint_indices, new int[] {4, 25});
-
-    Op floatingpoint_to_fp_real_ot = d_solver.mkOp(FLOATINGPOINT_TO_FP_REAL, 4, 25);
-    int[] floatingpoint_to_fp_real_indices = floatingpoint_to_fp_real_ot.getIntegerIndices();
-    assertArrayEquals(floatingpoint_to_fp_real_indices, new int[] {4, 25});
-
-    Op floatingpoint_to_fp_signed_bitvector_ot =
-        d_solver.mkOp(FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR, 4, 25);
-    int[] floatingpoint_to_fp_signed_bitvector_indices =
-        floatingpoint_to_fp_signed_bitvector_ot.getIntegerIndices();
-    assertArrayEquals(floatingpoint_to_fp_signed_bitvector_indices, new int[] {4, 25});
-
-    Op floatingpoint_to_fp_unsigned_bitvector_ot =
-        d_solver.mkOp(FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR, 4, 25);
-    int[] floatingpoint_to_fp_unsigned_bitvector_indices =
-        floatingpoint_to_fp_unsigned_bitvector_ot.getIntegerIndices();
-    assertArrayEquals(floatingpoint_to_fp_unsigned_bitvector_indices, new int[] {4, 25});
-
-    Op floatingpoint_to_fp_generic_ot = d_solver.mkOp(FLOATINGPOINT_TO_FP_GENERIC, 4, 25);
-    int[] floatingpoint_to_fp_generic_indices = floatingpoint_to_fp_generic_ot.getIntegerIndices();
-    assertArrayEquals(floatingpoint_to_fp_generic_indices, new int[] {4, 25});
-    assertThrows(CVC5ApiException.class, () -> floatingpoint_to_fp_generic_ot.getStringIndices());
-  }
-
-  @Test void opScopingToString() throws CVC5ApiException
-  {
-    Op bitvector_repeat_ot = d_solver.mkOp(BITVECTOR_REPEAT, 5);
-    String op_repr = bitvector_repeat_ot.toString();
-
-    Solver solver2;
-    assertEquals(bitvector_repeat_ot.toString(), op_repr);
-  }
-}
diff --git a/test/unit/api/java/cvc5/ResultTest.java b/test/unit/api/java/cvc5/ResultTest.java
deleted file mode 100644 (file)
index 8ba50c0..0000000
+++ /dev/null
@@ -1,126 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the Result class
- */
-
-package cvc5;
-
-import static org.junit.jupiter.api.Assertions.*;
-
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
-
-class ResultTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  @Test void isNull()
-  {
-    Result res_null = d_solver.getNullResult();
-    assertTrue(res_null.isNull());
-    assertFalse(res_null.isSat());
-    assertFalse(res_null.isUnsat());
-    assertFalse(res_null.isSatUnknown());
-    assertFalse(res_null.isEntailed());
-    assertFalse(res_null.isNotEntailed());
-    assertFalse(res_null.isEntailmentUnknown());
-    Sort u_sort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkVar(u_sort, "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    Result res = d_solver.checkSat();
-    assertFalse(res.isNull());
-  }
-
-  @Test void eq()
-  {
-    Sort u_sort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkVar(u_sort, "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    Result res;
-    Result res2 = d_solver.checkSat();
-    Result res3 = d_solver.checkSat();
-    res = res2;
-    assertEquals(res, res2);
-    assertEquals(res3, res2);
-  }
-
-  @Test void isSat()
-  {
-    Sort u_sort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkVar(u_sort, "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    Result res = d_solver.checkSat();
-    assertTrue(res.isSat());
-    assertFalse(res.isSatUnknown());
-  }
-
-  @Test void isUnsat()
-  {
-    Sort u_sort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkVar(u_sort, "x");
-    d_solver.assertFormula(x.eqTerm(x).notTerm());
-    Result res = d_solver.checkSat();
-    assertTrue(res.isUnsat());
-    assertFalse(res.isSatUnknown());
-  }
-
-  @Test void isSatUnknown() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_NIA");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("solve-int-as-bv", "32");
-    Sort int_sort = d_solver.getIntegerSort();
-    Term x = d_solver.mkVar(int_sort, "x");
-    d_solver.assertFormula(x.eqTerm(x).notTerm());
-    Result res = d_solver.checkSat();
-    assertFalse(res.isSat());
-    assertTrue(res.isSatUnknown());
-  }
-
-  @Test void isEntailed()
-  {
-    d_solver.setOption("incremental", "true");
-    Sort u_sort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkConst(u_sort, "x");
-    Term y = d_solver.mkConst(u_sort, "y");
-    Term a = x.eqTerm(y).notTerm();
-    Term b = x.eqTerm(y);
-    d_solver.assertFormula(a);
-    Result entailed = d_solver.checkEntailed(a);
-    assertTrue(entailed.isEntailed());
-    assertFalse(entailed.isEntailmentUnknown());
-    Result not_entailed = d_solver.checkEntailed(b);
-    assertTrue(not_entailed.isNotEntailed());
-    assertFalse(not_entailed.isEntailmentUnknown());
-  }
-
-  @Test void isEntailmentUnknown() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_NIA");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("solve-int-as-bv", "32");
-    Sort int_sort = d_solver.getIntegerSort();
-    Term x = d_solver.mkVar(int_sort, "x");
-    d_solver.assertFormula(x.eqTerm(x).notTerm());
-    Result res = d_solver.checkEntailed(x.eqTerm(x));
-    assertFalse(res.isEntailed());
-    assertTrue(res.isEntailmentUnknown());
-    assertEquals(res.getUnknownExplanation(), Result.UnknownExplanation.UNKNOWN_REASON);
-  }
-}
diff --git a/test/unit/api/java/cvc5/SolverTest.java b/test/unit/api/java/cvc5/SolverTest.java
deleted file mode 100644 (file)
index 971be58..0000000
+++ /dev/null
@@ -1,2558 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Mudathir Mohamed, Andrew Reynolds
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the Solver class of the Java API.
- */
-
-package cvc5;
-
-import static cvc5.Kind.*;
-import static cvc5.RoundingMode.*;
-import static org.junit.jupiter.api.Assertions.*;
-
-import java.math.BigInteger;
-import java.util.*;
-import java.util.concurrent.atomic.AtomicReference;
-import org.junit.jupiter.api.*;
-import org.junit.jupiter.api.function.Executable;
-
-class SolverTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  @Test void recoverableException() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x).notTerm());
-    assertThrows(CVC5ApiRecoverableException.class, () -> d_solver.getValue(x));
-  }
-
-  @Test void supportsFloatingPoint() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkRoundingMode(ROUND_NEAREST_TIES_TO_EVEN));
-  }
-
-  @Test void getBooleanSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.getBooleanSort());
-  }
-
-  @Test void getIntegerSort()
-  {
-    assertDoesNotThrow(() -> d_solver.getIntegerSort());
-  }
-
-  @Test void getNullSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.getNullSort());
-  }
-
-  @Test void getRealSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.getRealSort());
-  }
-
-  @Test void getRegExpSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.getRegExpSort());
-  }
-
-  @Test void getStringSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.getStringSort());
-  }
-
-  @Test void getRoundingModeSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.getRoundingModeSort());
-  }
-
-  @Test void mkArraySort() throws CVC5ApiException
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort intSort = d_solver.getIntegerSort();
-    Sort realSort = d_solver.getRealSort();
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertDoesNotThrow(() -> d_solver.mkArraySort(boolSort, boolSort));
-    assertDoesNotThrow(() -> d_solver.mkArraySort(intSort, intSort));
-    assertDoesNotThrow(() -> d_solver.mkArraySort(realSort, realSort));
-    assertDoesNotThrow(() -> d_solver.mkArraySort(bvSort, bvSort));
-    assertDoesNotThrow(() -> d_solver.mkArraySort(boolSort, intSort));
-    assertDoesNotThrow(() -> d_solver.mkArraySort(realSort, bvSort));
-
-    Sort fpSort = d_solver.mkFloatingPointSort(3, 5);
-    assertDoesNotThrow(() -> d_solver.mkArraySort(fpSort, fpSort));
-    assertDoesNotThrow(() -> d_solver.mkArraySort(bvSort, fpSort));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkArraySort(boolSort, boolSort));
-  }
-
-  @Test void mkBitVectorSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkBitVectorSort(32));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVectorSort(0));
-  }
-
-  @Test void mkFloatingPointSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkFloatingPointSort(4, 8));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPointSort(0, 8));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPointSort(4, 0));
-  }
-
-  @Test void mkDatatypeSort() throws CVC5ApiException
-  {
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    assertDoesNotThrow(() -> d_solver.mkDatatypeSort(dtypeSpec));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkDatatypeSort(dtypeSpec));
-
-    DatatypeDecl throwsDtypeSpec = d_solver.mkDatatypeDecl("list");
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkDatatypeSort(throwsDtypeSpec));
-  }
-
-  @Test void mkDatatypeSorts() throws CVC5ApiException
-  {
-    Solver slv = new Solver();
-
-    DatatypeDecl dtypeSpec1 = d_solver.mkDatatypeDecl("list1");
-    DatatypeConstructorDecl cons1 = d_solver.mkDatatypeConstructorDecl("cons1");
-    cons1.addSelector("head1", d_solver.getIntegerSort());
-    dtypeSpec1.addConstructor(cons1);
-    DatatypeConstructorDecl nil1 = d_solver.mkDatatypeConstructorDecl("nil1");
-    dtypeSpec1.addConstructor(nil1);
-    DatatypeDecl dtypeSpec2 = d_solver.mkDatatypeDecl("list2");
-    DatatypeConstructorDecl cons2 = d_solver.mkDatatypeConstructorDecl("cons2");
-    cons2.addSelector("head2", d_solver.getIntegerSort());
-    dtypeSpec2.addConstructor(cons2);
-    DatatypeConstructorDecl nil2 = d_solver.mkDatatypeConstructorDecl("nil2");
-    dtypeSpec2.addConstructor(nil2);
-    DatatypeDecl[] decls = {dtypeSpec1, dtypeSpec2};
-    assertDoesNotThrow(() -> d_solver.mkDatatypeSorts(decls));
-
-    assertThrows(CVC5ApiException.class, () -> slv.mkDatatypeSorts(decls));
-
-    DatatypeDecl throwsDtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeDecl[] throwsDecls = new DatatypeDecl[] {throwsDtypeSpec};
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkDatatypeSorts(throwsDecls));
-
-    /* with unresolved sorts */
-    Sort unresList = d_solver.mkUninterpretedSort("ulist");
-    Set<Sort> unresSorts = new HashSet<>();
-    unresSorts.add(unresList);
-    DatatypeDecl ulist = d_solver.mkDatatypeDecl("ulist");
-    DatatypeConstructorDecl ucons = d_solver.mkDatatypeConstructorDecl("ucons");
-    ucons.addSelector("car", unresList);
-    ucons.addSelector("cdr", unresList);
-    ulist.addConstructor(ucons);
-    DatatypeConstructorDecl unil = d_solver.mkDatatypeConstructorDecl("unil");
-    ulist.addConstructor(unil);
-    DatatypeDecl[] udecls = new DatatypeDecl[] {ulist};
-    assertDoesNotThrow(() -> d_solver.mkDatatypeSorts(Arrays.asList(udecls), unresSorts));
-
-    assertThrows(
-        CVC5ApiException.class, () -> slv.mkDatatypeSorts(Arrays.asList(udecls), unresSorts));
-
-    /* Note: More tests are in datatype_api_black. */
-  }
-
-  @Test void mkFunctionSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(()
-                           -> d_solver.mkFunctionSort(
-                               d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort()));
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    // function arguments are allowed
-    assertDoesNotThrow(() -> d_solver.mkFunctionSort(funSort, d_solver.getIntegerSort()));
-    // non-first-class arguments are not allowed
-    Sort reSort = d_solver.getRegExpSort();
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkFunctionSort(reSort, d_solver.getIntegerSort()));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkFunctionSort(d_solver.getIntegerSort(), funSort));
-
-    assertDoesNotThrow(()
-                           -> d_solver.mkFunctionSort(new Sort[] {d_solver.mkUninterpretedSort("u"),
-                                                          d_solver.getIntegerSort()},
-                               d_solver.getIntegerSort()));
-    Sort funSort2 =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    // function arguments are allowed
-    assertDoesNotThrow(
-        ()
-            -> d_solver.mkFunctionSort(new Sort[] {funSort2, d_solver.mkUninterpretedSort("u")},
-                d_solver.getIntegerSort()));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.mkFunctionSort(
-                new Sort[] {d_solver.getIntegerSort(), d_solver.mkUninterpretedSort("u")},
-                funSort2));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class,
-        () -> slv.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort()));
-
-    assertThrows(CVC5ApiException.class,
-        () -> slv.mkFunctionSort(slv.mkUninterpretedSort("u"), d_solver.getIntegerSort()));
-
-    Sort[] sorts1 =
-        new Sort[] {d_solver.getBooleanSort(), slv.getIntegerSort(), d_solver.getIntegerSort()};
-    Sort[] sorts2 = new Sort[] {slv.getBooleanSort(), slv.getIntegerSort()};
-    assertDoesNotThrow(() -> slv.mkFunctionSort(sorts2, slv.getIntegerSort()));
-    assertThrows(CVC5ApiException.class, () -> slv.mkFunctionSort(sorts1, slv.getIntegerSort()));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.mkFunctionSort(sorts2, d_solver.getIntegerSort()));
-  }
-
-  @Test void mkParamSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkParamSort("T"));
-    assertDoesNotThrow(() -> d_solver.mkParamSort(""));
-  }
-
-  @Test void mkPredicateSort()
-  {
-    assertDoesNotThrow(() -> d_solver.mkPredicateSort(new Sort[] {d_solver.getIntegerSort()}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkPredicateSort(new Sort[] {}));
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    // functions as arguments are allowed
-    assertDoesNotThrow(
-        () -> d_solver.mkPredicateSort(new Sort[] {d_solver.getIntegerSort(), funSort}));
-
-    Solver slv = new Solver();
-    assertThrows(
-        CVC5ApiException.class, () -> slv.mkPredicateSort(new Sort[] {d_solver.getIntegerSort()}));
-  }
-
-  @Test void mkRecordSort() throws CVC5ApiException
-  {
-    Pair<String, Sort>[] fields = new Pair[] {new Pair<>("b", d_solver.getBooleanSort()),
-        new Pair<>("bv", d_solver.mkBitVectorSort(8)),
-        new Pair<>("i", d_solver.getIntegerSort())};
-    Pair<String, Sort>[] empty = new Pair[0];
-    assertDoesNotThrow(() -> d_solver.mkRecordSort(fields));
-    assertDoesNotThrow(() -> d_solver.mkRecordSort(empty));
-    Sort recSort = d_solver.mkRecordSort(fields);
-    assertDoesNotThrow(() -> recSort.getDatatype());
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkRecordSort(fields));
-  }
-
-  @Test void mkSetSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkSetSort(d_solver.getBooleanSort()));
-    assertDoesNotThrow(() -> d_solver.mkSetSort(d_solver.getIntegerSort()));
-    assertDoesNotThrow(() -> d_solver.mkSetSort(d_solver.mkBitVectorSort(4)));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkSetSort(d_solver.mkBitVectorSort(4)));
-  }
-
-  @Test void mkBagSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkBagSort(d_solver.getBooleanSort()));
-    assertDoesNotThrow(() -> d_solver.mkBagSort(d_solver.getIntegerSort()));
-    assertDoesNotThrow(() -> d_solver.mkBagSort(d_solver.mkBitVectorSort(4)));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkBagSort(d_solver.mkBitVectorSort(4)));
-  }
-
-  @Test void mkSequenceSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkSequenceSort(d_solver.getBooleanSort()));
-    assertDoesNotThrow(
-        () -> d_solver.mkSequenceSort(d_solver.mkSequenceSort(d_solver.getIntegerSort())));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkSequenceSort(d_solver.getIntegerSort()));
-  }
-
-  @Test void mkUninterpretedSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkUninterpretedSort("u"));
-    assertDoesNotThrow(() -> d_solver.mkUninterpretedSort(""));
-  }
-
-  @Test void mkSortConstructorSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkSortConstructorSort("s", 2));
-    assertDoesNotThrow(() -> d_solver.mkSortConstructorSort("", 2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkSortConstructorSort("", 0));
-  }
-
-  @Test void mkTupleSort() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort()}));
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort(), funSort}));
-
-    Solver slv = new Solver();
-    assertThrows(
-        CVC5ApiException.class, () -> slv.mkTupleSort(new Sort[] {d_solver.getIntegerSort()}));
-  }
-
-  @Test void mkBitVector() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, 2));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(32, 2));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "-1111111", 2));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "0101", 2));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "00000101", 2));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "-127", 10));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "255", 10));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "-7f", 16));
-    assertDoesNotThrow(() -> d_solver.mkBitVector(8, "a0", 16));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(0, 2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(0, "-127", 10));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(0, "a0", 16));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "", 2));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "101", 5));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "128", 11));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "a0", 21));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-11111111", 2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "101010101", 2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-256", 10));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "257", 10));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-a0", 16));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "fffff", 16));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "10201010", 2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "-25x", 10));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "2x7", 10));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkBitVector(8, "fzff", 16));
-
-    assertEquals(d_solver.mkBitVector(8, "0101", 2), d_solver.mkBitVector(8, "00000101", 2));
-    assertEquals(d_solver.mkBitVector(4, "-1", 2), d_solver.mkBitVector(4, "1111", 2));
-    assertEquals(d_solver.mkBitVector(4, "-1", 16), d_solver.mkBitVector(4, "1111", 2));
-    assertEquals(d_solver.mkBitVector(4, "-1", 10), d_solver.mkBitVector(4, "1111", 2));
-    assertEquals(d_solver.mkBitVector(8, "01010101", 2).toString(), "#b01010101");
-    assertEquals(d_solver.mkBitVector(8, "F", 16).toString(), "#b00001111");
-    assertEquals(d_solver.mkBitVector(8, "-1", 10), d_solver.mkBitVector(8, "FF", 16));
-  }
-
-  @Test void mkVar() throws CVC5ApiException
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort intSort = d_solver.getIntegerSort();
-    Sort funSort = d_solver.mkFunctionSort(intSort, boolSort);
-    assertDoesNotThrow(() -> d_solver.mkVar(boolSort));
-    assertDoesNotThrow(() -> d_solver.mkVar(funSort));
-    assertDoesNotThrow(() -> d_solver.mkVar(boolSort, ("b")));
-    assertDoesNotThrow(() -> d_solver.mkVar(funSort, ""));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkVar(d_solver.getNullSort()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkVar(d_solver.getNullSort(), "a"));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkVar(boolSort, "x"));
-  }
-
-  @Test void mkBoolean() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkBoolean(true));
-    assertDoesNotThrow(() -> d_solver.mkBoolean(false));
-  }
-
-  @Test void mkRoundingMode() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkRoundingMode(RoundingMode.ROUND_TOWARD_ZERO));
-  }
-
-  @Test void mkUninterpretedConst() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkUninterpretedConst(d_solver.getBooleanSort(), 1));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkUninterpretedConst(d_solver.getNullSort(), 1));
-    Solver slv = new Solver();
-    assertThrows(
-        CVC5ApiException.class, () -> slv.mkUninterpretedConst(d_solver.getBooleanSort(), 1));
-  }
-
-  @Test void mkAbstractValue() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkAbstractValue(("1")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(("0")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(("-1")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(("1.2")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue("1/2"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue("asdf"));
-
-    assertDoesNotThrow(() -> d_solver.mkAbstractValue((int) 1));
-    assertDoesNotThrow(() -> d_solver.mkAbstractValue((int) 1));
-    assertDoesNotThrow(() -> d_solver.mkAbstractValue((long) 1));
-    assertDoesNotThrow(() -> d_solver.mkAbstractValue((long) 1));
-    // java does not have specific types for unsigned integers, therefore the two lines below do not
-    // make sense in java. assertDoesNotThrow(() -> d_solver.mkAbstractValue((int)-1));
-    // assertDoesNotThrow(() -> d_solver.mkAbstractValue((long)-1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkAbstractValue(0));
-  }
-
-  @Test void mkFloatingPoint() throws CVC5ApiException
-  {
-    Term t1 = d_solver.mkBitVector(8);
-    Term t2 = d_solver.mkBitVector(4);
-    Term t3 = d_solver.mkInteger(2);
-    assertDoesNotThrow(() -> d_solver.mkFloatingPoint(3, 5, t1));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkFloatingPoint(0, 5, d_solver.getNullTerm()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(0, 5, t1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(3, 0, t1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(3, 5, t2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkFloatingPoint(3, 5, t2));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkFloatingPoint(3, 5, t1));
-  }
-
-  @Test void mkEmptySet() throws CVC5ApiException
-  {
-    Solver slv = new Solver();
-    Sort s = d_solver.mkSetSort(d_solver.getBooleanSort());
-    assertDoesNotThrow(() -> d_solver.mkEmptySet(d_solver.getNullSort()));
-    assertDoesNotThrow(() -> d_solver.mkEmptySet(s));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkEmptySet(d_solver.getBooleanSort()));
-    assertThrows(CVC5ApiException.class, () -> slv.mkEmptySet(s));
-  }
-
-  @Test void mkEmptyBag() throws CVC5ApiException
-  {
-    Solver slv = new Solver();
-    Sort s = d_solver.mkBagSort(d_solver.getBooleanSort());
-    assertDoesNotThrow(() -> d_solver.mkEmptyBag(d_solver.getNullSort()));
-    assertDoesNotThrow(() -> d_solver.mkEmptyBag(s));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkEmptyBag(d_solver.getBooleanSort()));
-
-    assertThrows(CVC5ApiException.class, () -> slv.mkEmptyBag(s));
-  }
-
-  @Test void mkEmptySequence() throws CVC5ApiException
-  {
-    Solver slv = new Solver();
-    Sort s = d_solver.mkSequenceSort(d_solver.getBooleanSort());
-    assertDoesNotThrow(() -> d_solver.mkEmptySequence(s));
-    assertDoesNotThrow(() -> d_solver.mkEmptySequence(d_solver.getBooleanSort()));
-    assertThrows(CVC5ApiException.class, () -> slv.mkEmptySequence(s));
-  }
-
-  @Test void mkFalse() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkFalse());
-    assertDoesNotThrow(() -> d_solver.mkFalse());
-  }
-
-  @Test void mkNaN() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkNaN(3, 5));
-  }
-
-  @Test void mkNegZero() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.mkNegZero(3, 5));
-  }
-
-  @Test void mkNegInf()
-  {
-    assertDoesNotThrow(() -> d_solver.mkNegInf(3, 5));
-  }
-
-  @Test void mkPosInf()
-  {
-    assertDoesNotThrow(() -> d_solver.mkPosInf(3, 5));
-  }
-
-  @Test void mkPosZero()
-  {
-    assertDoesNotThrow(() -> d_solver.mkPosZero(3, 5));
-  }
-
-  @Test void mkOp()
-  {
-    // Unlike c++,  mkOp(Kind kind, Kind k) is a type error in java
-    // assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT, EQUAL));
-
-    // mkOp(Kind kind, const std::string& arg)
-    assertDoesNotThrow(() -> d_solver.mkOp(DIVISIBLE, "2147483648"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT, "asdf"));
-
-    // mkOp(Kind kind, int arg)
-    assertDoesNotThrow(() -> d_solver.mkOp(DIVISIBLE, 1));
-    assertDoesNotThrow(() -> d_solver.mkOp(BITVECTOR_ROTATE_LEFT, 1));
-    assertDoesNotThrow(() -> d_solver.mkOp(BITVECTOR_ROTATE_RIGHT, 1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(BITVECTOR_EXTRACT, 1));
-
-    // mkOp(Kind kind, int arg1, int arg2)
-    assertDoesNotThrow(() -> d_solver.mkOp(BITVECTOR_EXTRACT, 1, 1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkOp(DIVISIBLE, 1, 2));
-
-    // mkOp(Kind kind, int[] args)
-    int[] args = new int[] {1, 2, 2};
-    assertDoesNotThrow(() -> d_solver.mkOp(TUPLE_PROJECT, args));
-  }
-
-  @Test void mkPi()
-  {
-    assertDoesNotThrow(() -> d_solver.mkPi());
-  }
-
-  @Test void mkInteger()
-  {
-    assertDoesNotThrow(() -> d_solver.mkInteger("123"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("1.23"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("1/23"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("12/3"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(".2"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("2."));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(""));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("asdf"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("1.2/3"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("."));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("/"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("2/"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("/2"));
-
-    assertDoesNotThrow(() -> d_solver.mkReal(("123")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("1.23")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("1/23")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("12/3")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger((".2")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("2.")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("asdf")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("1.2/3")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger((".")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("/")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("2/")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(("/2")));
-
-    int val1 = 1;
-    long val2 = -1;
-    int val3 = 1;
-    long val4 = -1;
-    assertDoesNotThrow(() -> d_solver.mkInteger(val1));
-    assertDoesNotThrow(() -> d_solver.mkInteger(val2));
-    assertDoesNotThrow(() -> d_solver.mkInteger(val3));
-    assertDoesNotThrow(() -> d_solver.mkInteger(val4));
-    assertDoesNotThrow(() -> d_solver.mkInteger(val4));
-  }
-
-  @Test void mkReal()
-  {
-    assertDoesNotThrow(() -> d_solver.mkReal("123"));
-    assertDoesNotThrow(() -> d_solver.mkReal("1.23"));
-    assertDoesNotThrow(() -> d_solver.mkReal("1/23"));
-    assertDoesNotThrow(() -> d_solver.mkReal("12/3"));
-    assertDoesNotThrow(() -> d_solver.mkReal(".2"));
-    assertDoesNotThrow(() -> d_solver.mkReal("2."));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(""));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("asdf"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("1.2/3"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("."));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("/"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("2/"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal("/2"));
-
-    assertDoesNotThrow(() -> d_solver.mkReal(("123")));
-    assertDoesNotThrow(() -> d_solver.mkReal(("1.23")));
-    assertDoesNotThrow(() -> d_solver.mkReal(("1/23")));
-    assertDoesNotThrow(() -> d_solver.mkReal(("12/3")));
-    assertDoesNotThrow(() -> d_solver.mkReal((".2")));
-    assertDoesNotThrow(() -> d_solver.mkReal(("2.")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("asdf")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("1.2/3")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal((".")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("/")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("2/")));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkReal(("/2")));
-
-    int val1 = 1;
-    long val2 = -1;
-    int val3 = 1;
-    long val4 = -1;
-    assertDoesNotThrow(() -> d_solver.mkReal(val1));
-    assertDoesNotThrow(() -> d_solver.mkReal(val2));
-    assertDoesNotThrow(() -> d_solver.mkReal(val3));
-    assertDoesNotThrow(() -> d_solver.mkReal(val4));
-    assertDoesNotThrow(() -> d_solver.mkReal(val4));
-    assertDoesNotThrow(() -> d_solver.mkReal(val1, val1));
-    assertDoesNotThrow(() -> d_solver.mkReal(val2, val2));
-    assertDoesNotThrow(() -> d_solver.mkReal(val3, val3));
-    assertDoesNotThrow(() -> d_solver.mkReal(val4, val4));
-  }
-
-  @Test void mkRegexpEmpty()
-  {
-    Sort strSort = d_solver.getStringSort();
-    Term s = d_solver.mkConst(strSort, "s");
-    assertDoesNotThrow(() -> d_solver.mkTerm(STRING_IN_REGEXP, s, d_solver.mkRegexpEmpty()));
-  }
-
-  @Test void mkRegexpSigma()
-  {
-    Sort strSort = d_solver.getStringSort();
-    Term s = d_solver.mkConst(strSort, "s");
-    assertDoesNotThrow(() -> d_solver.mkTerm(STRING_IN_REGEXP, s, d_solver.mkRegexpSigma()));
-  }
-
-  @Test void mkSepEmp()
-  {
-    assertDoesNotThrow(() -> d_solver.mkSepEmp());
-  }
-
-  @Test void mkSepNil()
-  {
-    assertDoesNotThrow(() -> d_solver.mkSepNil(d_solver.getBooleanSort()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkSepNil(d_solver.getNullSort()));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkSepNil(d_solver.getIntegerSort()));
-  }
-
-  @Test void mkString()
-  {
-    assertDoesNotThrow(() -> d_solver.mkString(""));
-    assertDoesNotThrow(() -> d_solver.mkString("asdfasdf"));
-    assertEquals(d_solver.mkString("asdf\\nasdf").toString(), "\"asdf\\u{5c}nasdf\"");
-    assertEquals(d_solver.mkString("asdf\\u{005c}nasdf", true).toString(), "\"asdf\\u{5c}nasdf\"");
-  }
-
-  @Test void mkTerm() throws CVC5ApiException
-  {
-    Sort bv32 = d_solver.mkBitVectorSort(32);
-    Term a = d_solver.mkConst(bv32, "a");
-    Term b = d_solver.mkConst(bv32, "b");
-    Term[] v1 = new Term[] {a, b};
-    Term[] v2 = new Term[] {a, d_solver.getNullTerm()};
-    Term[] v3 = new Term[] {a, d_solver.mkTrue()};
-    Term[] v4 = new Term[] {d_solver.mkInteger(1), d_solver.mkInteger(2)};
-    Term[] v5 = new Term[] {d_solver.mkInteger(1), d_solver.getNullTerm()};
-    Term[] v6 = new Term[] {};
-    Solver slv = new Solver();
-
-    // mkTerm(Kind kind) const
-    assertDoesNotThrow(() -> d_solver.mkTerm(PI));
-    assertDoesNotThrow(() -> d_solver.mkTerm(REGEXP_EMPTY));
-    assertDoesNotThrow(() -> d_solver.mkTerm(REGEXP_SIGMA));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(CONST_BITVECTOR));
-
-    // mkTerm(Kind kind, Term child) const
-    assertDoesNotThrow(() -> d_solver.mkTerm(NOT, d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(NOT, d_solver.getNullTerm()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(NOT, a));
-    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(NOT, d_solver.mkTrue()));
-
-    // mkTerm(Kind kind, Term child1, Term child2) const
-    assertDoesNotThrow(() -> d_solver.mkTerm(EQUAL, a, b));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, d_solver.getNullTerm(), b));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, a, d_solver.getNullTerm()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, a, d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(EQUAL, a, b));
-
-    // mkTerm(Kind kind, Term child1, Term child2, Term child3) const
-    assertDoesNotThrow(
-        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(ITE, d_solver.getNullTerm(), d_solver.mkTrue(), d_solver.mkTrue()));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.getNullTerm(), d_solver.mkTrue()));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), d_solver.getNullTerm()));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), b));
-
-    assertThrows(CVC5ApiException.class,
-        () -> slv.mkTerm(ITE, d_solver.mkTrue(), d_solver.mkTrue(), d_solver.mkTrue()));
-
-    // mkTerm(Kind kind, const Term[]& children) const
-    assertDoesNotThrow(() -> d_solver.mkTerm(EQUAL, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, v2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(EQUAL, v3));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(DISTINCT, v6));
-  }
-
-  @Test void mkTermFromOp() throws CVC5ApiException
-  {
-    Sort bv32 = d_solver.mkBitVectorSort(32);
-    Term a = d_solver.mkConst(bv32, "a");
-    Term b = d_solver.mkConst(bv32, "b");
-    Term[] v1 = new Term[] {d_solver.mkInteger(1), d_solver.mkInteger(2)};
-    Term[] v2 = new Term[] {d_solver.mkInteger(1), d_solver.getNullTerm()};
-    Term[] v3 = new Term[] {};
-    Term[] v4 = new Term[] {d_solver.mkInteger(5)};
-    Solver slv = new Solver();
-
-    // simple operator terms
-    Op opterm1 = d_solver.mkOp(BITVECTOR_EXTRACT, 2, 1);
-    Op opterm2 = d_solver.mkOp(DIVISIBLE, 1);
-
-    // list datatype
-    Sort sort = d_solver.mkParamSort("T");
-    DatatypeDecl listDecl = d_solver.mkDatatypeDecl("paramlist", sort);
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    cons.addSelector("head", sort);
-    cons.addSelectorSelf("tail");
-    listDecl.addConstructor(cons);
-    listDecl.addConstructor(nil);
-    Sort listSort = d_solver.mkDatatypeSort(listDecl);
-    Sort intListSort = listSort.instantiate(new Sort[] {d_solver.getIntegerSort()});
-    Term c = d_solver.mkConst(intListSort, "c");
-    Datatype list = listSort.getDatatype();
-
-    // list datatype constructor and selector operator terms
-    Term consTerm1 = list.getConstructorTerm("cons");
-    Term consTerm2 = list.getConstructor("cons").getConstructorTerm();
-    Term nilTerm1 = list.getConstructorTerm("nil");
-    Term nilTerm2 = list.getConstructor("nil").getConstructorTerm();
-    Term headTerm1 = list.getConstructor("cons").getSelectorTerm("head");
-    Term headTerm2 = list.getConstructor("cons").getSelector("head").getSelectorTerm();
-    Term tailTerm1 = list.getConstructor("cons").getSelectorTerm("tail");
-    Term tailTerm2 = list.getConstructor("cons").getSelector("tail").getSelectorTerm();
-
-    // mkTerm(Op op, Term term) const
-    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm1));
-    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_SELECTOR, nilTerm1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_SELECTOR, consTerm1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_CONSTRUCTOR, consTerm2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(APPLY_SELECTOR, headTerm1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1));
-    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(APPLY_CONSTRUCTOR, nilTerm1));
-
-    // mkTerm(Op op, Term child) const
-    assertDoesNotThrow(() -> d_solver.mkTerm(opterm1, a));
-    assertDoesNotThrow(() -> d_solver.mkTerm(opterm2, d_solver.mkInteger(1)));
-    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_SELECTOR, headTerm1, c));
-    assertDoesNotThrow(() -> d_solver.mkTerm(APPLY_SELECTOR, tailTerm2, c));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, a));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1, d_solver.getNullTerm()));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(APPLY_CONSTRUCTOR, consTerm1, d_solver.mkInteger(0)));
-
-    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(opterm1, a));
-
-    // mkTerm(Op op, Term child1, Term child2) const
-    assertDoesNotThrow(()
-                           -> d_solver.mkTerm(APPLY_CONSTRUCTOR,
-                               consTerm1,
-                               d_solver.mkInteger(0),
-                               d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm1)));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(opterm2, d_solver.mkInteger(1), d_solver.mkInteger(2)));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1, a, b));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(opterm2, d_solver.mkInteger(1), d_solver.getNullTerm()));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(opterm2, d_solver.getNullTerm(), d_solver.mkInteger(1)));
-
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.mkTerm(APPLY_CONSTRUCTOR,
-                consTerm1,
-                d_solver.mkInteger(0),
-                d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm1)));
-
-    // mkTerm(Op op, Term child1, Term child2, Term child3) const
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm1, a, b, a));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.mkTerm(
-                opterm2, d_solver.mkInteger(1), d_solver.mkInteger(1), d_solver.getNullTerm()));
-
-    // mkTerm(Op op, Term[] children)
-    assertDoesNotThrow(() -> d_solver.mkTerm(opterm2, v4));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, v2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkTerm(opterm2, v3));
-    assertThrows(CVC5ApiException.class, () -> slv.mkTerm(opterm2, v4));
-  }
-
-  @Test void mkTrue()
-  {
-    assertDoesNotThrow(() -> d_solver.mkTrue());
-    assertDoesNotThrow(() -> d_solver.mkTrue());
-  }
-
-  @Test void mkTuple()
-  {
-    assertDoesNotThrow(()
-                           -> d_solver.mkTuple(new Sort[] {d_solver.mkBitVectorSort(3)},
-                               new Term[] {d_solver.mkBitVector(3, "101", 2)}));
-    assertDoesNotThrow(()
-                           -> d_solver.mkTuple(new Sort[] {d_solver.getRealSort()},
-                               new Term[] {d_solver.mkInteger("5")}));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTuple(new Sort[] {}, new Term[] {d_solver.mkBitVector(3, "101", 2)}));
-
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.mkTuple(new Sort[] {d_solver.mkBitVectorSort(4)},
-                new Term[] {d_solver.mkBitVector(3, "101", 2)}));
-
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.mkTuple(
-                new Sort[] {d_solver.getIntegerSort()}, new Term[] {d_solver.mkReal("5.3")}));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.mkTuple(new Sort[] {d_solver.mkBitVectorSort(3)},
-                new Term[] {slv.mkBitVector(3, "101", 2)}));
-
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.mkTuple(new Sort[] {slv.mkBitVectorSort(3)},
-                new Term[] {d_solver.mkBitVector(3, "101", 2)}));
-  }
-
-  @Test void mkUniverseSet()
-  {
-    assertDoesNotThrow(() -> d_solver.mkUniverseSet(d_solver.getBooleanSort()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkUniverseSet(d_solver.getNullSort()));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkUniverseSet(d_solver.getBooleanSort()));
-  }
-
-  @Test void mkConst()
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort intSort = d_solver.getIntegerSort();
-    Sort funSort = d_solver.mkFunctionSort(intSort, boolSort);
-    assertDoesNotThrow(() -> d_solver.mkConst(boolSort));
-    assertDoesNotThrow(() -> d_solver.mkConst(funSort));
-    assertDoesNotThrow(() -> d_solver.mkConst(boolSort, ("b")));
-    assertDoesNotThrow(() -> d_solver.mkConst(intSort, ("i")));
-    assertDoesNotThrow(() -> d_solver.mkConst(funSort, "f"));
-    assertDoesNotThrow(() -> d_solver.mkConst(funSort, ""));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkConst(d_solver.getNullSort()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkConst(d_solver.getNullSort(), "a"));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkConst(boolSort));
-  }
-
-  @Test void mkConstArray()
-  {
-    Sort intSort = d_solver.getIntegerSort();
-    Sort arrSort = d_solver.mkArraySort(intSort, intSort);
-    Term zero = d_solver.mkInteger(0);
-    Term constArr = d_solver.mkConstArray(arrSort, zero);
-
-    assertDoesNotThrow(() -> d_solver.mkConstArray(arrSort, zero));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkConstArray(d_solver.getNullSort(), zero));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkConstArray(arrSort, d_solver.getNullTerm()));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkConstArray(arrSort, d_solver.mkBitVector(1, 1)));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkConstArray(intSort, zero));
-    Solver slv = new Solver();
-    Term zero2 = slv.mkInteger(0);
-    Sort arrSort2 = slv.mkArraySort(slv.getIntegerSort(), slv.getIntegerSort());
-    assertThrows(CVC5ApiException.class, () -> slv.mkConstArray(arrSort2, zero));
-    assertThrows(CVC5ApiException.class, () -> slv.mkConstArray(arrSort, zero2));
-  }
-
-  @Test void declareDatatype()
-  {
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    DatatypeConstructorDecl[] ctors1 = new DatatypeConstructorDecl[] {nil};
-    assertDoesNotThrow(() -> d_solver.declareDatatype(("a"), ctors1));
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    DatatypeConstructorDecl nil2 = d_solver.mkDatatypeConstructorDecl("nil");
-    DatatypeConstructorDecl[] ctors2 = new DatatypeConstructorDecl[] {cons, nil2};
-    assertDoesNotThrow(() -> d_solver.declareDatatype(("b"), ctors2));
-    DatatypeConstructorDecl cons2 = d_solver.mkDatatypeConstructorDecl("cons");
-    DatatypeConstructorDecl nil3 = d_solver.mkDatatypeConstructorDecl("nil");
-    DatatypeConstructorDecl[] ctors3 = new DatatypeConstructorDecl[] {cons2, nil3};
-    assertDoesNotThrow(() -> d_solver.declareDatatype((""), ctors3));
-    DatatypeConstructorDecl[] ctors4 = new DatatypeConstructorDecl[0];
-    assertThrows(CVC5ApiException.class, () -> d_solver.declareDatatype(("c"), ctors4));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.declareDatatype((""), ctors4));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.declareDatatype(("a"), ctors1));
-  }
-
-  @Test void declareFun() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    assertDoesNotThrow(() -> d_solver.declareFun("f1", new Sort[] {}, bvSort));
-    assertDoesNotThrow(
-        () -> d_solver.declareFun("f3", new Sort[] {bvSort, d_solver.getIntegerSort()}, bvSort));
-    assertThrows(CVC5ApiException.class, () -> d_solver.declareFun("f2", new Sort[] {}, funSort));
-    // functions as arguments is allowed
-    assertDoesNotThrow(() -> d_solver.declareFun("f4", new Sort[] {bvSort, funSort}, bvSort));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.declareFun("f5", new Sort[] {bvSort, bvSort}, funSort));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.declareFun("f1", new Sort[] {}, bvSort));
-  }
-
-  @Test void declareSort()
-  {
-    assertDoesNotThrow(() -> d_solver.declareSort("s", 0));
-    assertDoesNotThrow(() -> d_solver.declareSort("s", 2));
-    assertDoesNotThrow(() -> d_solver.declareSort("", 2));
-  }
-
-  @Test void defineSort()
-  {
-    Sort sortVar0 = d_solver.mkParamSort("T0");
-    Sort sortVar1 = d_solver.mkParamSort("T1");
-    Sort intSort = d_solver.getIntegerSort();
-    Sort realSort = d_solver.getRealSort();
-    Sort arraySort0 = d_solver.mkArraySort(sortVar0, sortVar0);
-    Sort arraySort1 = d_solver.mkArraySort(sortVar0, sortVar1);
-    // Now create instantiations of the defined sorts
-    assertDoesNotThrow(() -> arraySort0.substitute(sortVar0, intSort));
-    assertDoesNotThrow(()
-                           -> arraySort1.substitute(
-                               new Sort[] {sortVar0, sortVar1}, new Sort[] {intSort, realSort}));
-  }
-
-  @Test void defineFun() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
-    Sort funSort2 =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    Term b1 = d_solver.mkVar(bvSort, "b1");
-    Term b11 = d_solver.mkVar(bvSort, "b1");
-    Term b2 = d_solver.mkVar(d_solver.getIntegerSort(), "b2");
-    Term b3 = d_solver.mkVar(funSort2, "b3");
-    Term v1 = d_solver.mkConst(bvSort, "v1");
-    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
-    Term v3 = d_solver.mkConst(funSort2, "v3");
-    Term f1 = d_solver.mkConst(funSort1, "f1");
-    Term f2 = d_solver.mkConst(funSort2, "f2");
-    Term f3 = d_solver.mkConst(bvSort, "f3");
-    assertDoesNotThrow(() -> d_solver.defineFun("f", new Term[] {}, bvSort, v1));
-    assertDoesNotThrow(() -> d_solver.defineFun("ff", new Term[] {b1, b2}, bvSort, v1));
-    assertDoesNotThrow(() -> d_solver.defineFun(f1, new Term[] {b1, b11}, v1));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFun("ff", new Term[] {v1, b2}, bvSort, v1));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFun("fff", new Term[] {b1}, bvSort, v3));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFun("ffff", new Term[] {b1}, funSort2, v3));
-
-    // b3 has function sort, which is allowed as an argument
-    assertDoesNotThrow(() -> d_solver.defineFun("fffff", new Term[] {b1, b3}, bvSort, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {v1, b11}, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {b1}, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {b1, b11}, v2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f1, new Term[] {b1, b11}, v3));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f2, new Term[] {b1}, v2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFun(f3, new Term[] {b1}, v1));
-
-    Solver slv = new Solver();
-    Sort bvSort2 = slv.mkBitVectorSort(32);
-    Term v12 = slv.mkConst(bvSort2, "v1");
-    Term b12 = slv.mkVar(bvSort2, "b1");
-    Term b22 = slv.mkVar(slv.getIntegerSort(), "b2");
-    assertThrows(CVC5ApiException.class, () -> slv.defineFun("f", new Term[] {}, bvSort, v12));
-    assertThrows(CVC5ApiException.class, () -> slv.defineFun("f", new Term[] {}, bvSort2, v1));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b1, b22}, bvSort2, v12));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b12, b2}, bvSort2, v12));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b12, b22}, bvSort, v12));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFun("ff", new Term[] {b12, b22}, bvSort2, v1));
-  }
-
-  @Test void defineFunGlobal()
-  {
-    Sort bSort = d_solver.getBooleanSort();
-    Sort fSort = d_solver.mkFunctionSort(bSort, bSort);
-
-    Term bTrue = d_solver.mkBoolean(true);
-    // (define-fun f () Bool true)
-    Term f = d_solver.defineFun("f", new Term[] {}, bSort, bTrue, true);
-    Term b = d_solver.mkVar(bSort, "b");
-    Term gSym = d_solver.mkConst(fSort, "g");
-    // (define-fun g (b Bool) Bool b)
-    Term g = d_solver.defineFun(gSym, new Term[] {b}, b, true);
-
-    // (assert (or (not f) (not (g true))))
-    d_solver.assertFormula(
-        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
-    assertTrue(d_solver.checkSat().isUnsat());
-    d_solver.resetAssertions();
-    // (assert (or (not f) (not (g true))))
-    d_solver.assertFormula(
-        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
-    assertTrue(d_solver.checkSat().isUnsat());
-  }
-
-  @Test void defineFunRec() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
-    Sort funSort2 =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    Term b1 = d_solver.mkVar(bvSort, "b1");
-    Term b11 = d_solver.mkVar(bvSort, "b1");
-    Term b2 = d_solver.mkVar(d_solver.getIntegerSort(), "b2");
-    Term b3 = d_solver.mkVar(funSort2, "b3");
-    Term v1 = d_solver.mkConst(bvSort, "v1");
-    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
-    Term v3 = d_solver.mkConst(funSort2, "v3");
-    Term f1 = d_solver.mkConst(funSort1, "f1");
-    Term f2 = d_solver.mkConst(funSort2, "f2");
-    Term f3 = d_solver.mkConst(bvSort, "f3");
-    assertDoesNotThrow(() -> d_solver.defineFunRec("f", new Term[] {}, bvSort, v1));
-    assertDoesNotThrow(() -> d_solver.defineFunRec("ff", new Term[] {b1, b2}, bvSort, v1));
-    assertDoesNotThrow(() -> d_solver.defineFunRec(f1, new Term[] {b1, b11}, v1));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFunRec("fff", new Term[] {b1}, bvSort, v3));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFunRec("ff", new Term[] {b1, v2}, bvSort, v1));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFunRec("ffff", new Term[] {b1}, funSort2, v3));
-
-    // b3 has function sort, which is allowed as an argument
-    assertDoesNotThrow(() -> d_solver.defineFunRec("fffff", new Term[] {b1, b3}, bvSort, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f1, new Term[] {b1}, v1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f1, new Term[] {b1, b11}, v2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f1, new Term[] {b1, b11}, v3));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f2, new Term[] {b1}, v2));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f3, new Term[] {b1}, v1));
-
-    Solver slv = new Solver();
-    Sort bvSort2 = slv.mkBitVectorSort(32);
-    Term v12 = slv.mkConst(bvSort2, "v1");
-    Term b12 = slv.mkVar(bvSort2, "b1");
-    Term b22 = slv.mkVar(slv.getIntegerSort(), "b2");
-    assertDoesNotThrow(() -> slv.defineFunRec("f", new Term[] {}, bvSort2, v12));
-    assertDoesNotThrow(() -> slv.defineFunRec("ff", new Term[] {b12, b22}, bvSort2, v12));
-    assertThrows(CVC5ApiException.class, () -> slv.defineFunRec("f", new Term[] {}, bvSort, v12));
-    assertThrows(CVC5ApiException.class, () -> slv.defineFunRec("f", new Term[] {}, bvSort2, v1));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b1, b22}, bvSort2, v12));
-
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b12, b2}, bvSort2, v12));
-
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b12, b22}, bvSort, v12));
-
-    assertThrows(
-        CVC5ApiException.class, () -> slv.defineFunRec("ff", new Term[] {b12, b22}, bvSort2, v1));
-  }
-
-  @Test void defineFunRecWrongLogic() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_BV");
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort funSort = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
-    Term b = d_solver.mkVar(bvSort, "b");
-    Term v = d_solver.mkConst(bvSort, "v");
-    Term f = d_solver.mkConst(funSort, "f");
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.defineFunRec("f", new Term[] {}, bvSort, v));
-    assertThrows(CVC5ApiException.class, () -> d_solver.defineFunRec(f, new Term[] {b, b}, v));
-  }
-
-  @Test void defineFunRecGlobal() throws CVC5ApiException
-  {
-    Sort bSort = d_solver.getBooleanSort();
-    Sort fSort = d_solver.mkFunctionSort(bSort, bSort);
-
-    d_solver.push();
-    Term bTrue = d_solver.mkBoolean(true);
-    // (define-fun f () Bool true)
-    Term f = d_solver.defineFunRec("f", new Term[] {}, bSort, bTrue, true);
-    Term b = d_solver.mkVar(bSort, "b");
-    Term gSym = d_solver.mkConst(fSort, "g");
-    // (define-fun g (b Bool) Bool b)
-    Term g = d_solver.defineFunRec(gSym, new Term[] {b}, b, true);
-
-    // (assert (or (not f) (not (g true))))
-    d_solver.assertFormula(
-        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
-    assertTrue(d_solver.checkSat().isUnsat());
-    d_solver.pop();
-    // (assert (or (not f) (not (g true))))
-    d_solver.assertFormula(
-        d_solver.mkTerm(OR, f.notTerm(), d_solver.mkTerm(APPLY_UF, g, bTrue).notTerm()));
-    assertTrue(d_solver.checkSat().isUnsat());
-  }
-
-  @Test void defineFunsRec() throws CVC5ApiException
-  {
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
-    Sort funSort2 = d_solver.mkFunctionSort(uSort, d_solver.getIntegerSort());
-    Term b1 = d_solver.mkVar(bvSort, "b1");
-    Term b11 = d_solver.mkVar(bvSort, "b1");
-    Term b2 = d_solver.mkVar(d_solver.getIntegerSort(), "b2");
-    Term b3 = d_solver.mkVar(funSort2, "b3");
-    Term b4 = d_solver.mkVar(uSort, "b4");
-    Term v1 = d_solver.mkConst(bvSort, "v1");
-    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
-    Term v3 = d_solver.mkConst(funSort2, "v3");
-    Term v4 = d_solver.mkConst(uSort, "v4");
-    Term f1 = d_solver.mkConst(funSort1, "f1");
-    Term f2 = d_solver.mkConst(funSort2, "f2");
-    Term f3 = d_solver.mkConst(bvSort, "f3");
-    assertDoesNotThrow(
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f2}, new Term[][] {{b1, b11}, {b4}}, new Term[] {v1, v2}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f2}, new Term[][] {{v1, b11}, {b4}}, new Term[] {v1, v2}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f3}, new Term[][] {{b1, b11}, {b4}}, new Term[] {v1, v2}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f2}, new Term[][] {{b1}, {b4}}, new Term[] {v1, v2}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f2}, new Term[][] {{b1, b2}, {b4}}, new Term[] {v1, v2}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f2}, new Term[][] {{b1, b11}, {b4}}, new Term[] {v1, v4}));
-
-    Solver slv = new Solver();
-    Sort uSort2 = slv.mkUninterpretedSort("u");
-    Sort bvSort2 = slv.mkBitVectorSort(32);
-    Sort funSort12 = slv.mkFunctionSort(new Sort[] {bvSort2, bvSort2}, bvSort2);
-    Sort funSort22 = slv.mkFunctionSort(uSort2, slv.getIntegerSort());
-    Term b12 = slv.mkVar(bvSort2, "b1");
-    Term b112 = slv.mkVar(bvSort2, "b1");
-    Term b42 = slv.mkVar(uSort2, "b4");
-    Term v12 = slv.mkConst(bvSort2, "v1");
-    Term v22 = slv.mkConst(slv.getIntegerSort(), "v2");
-    Term f12 = slv.mkConst(funSort12, "f1");
-    Term f22 = slv.mkConst(funSort22, "f2");
-    assertDoesNotThrow(
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f1, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f2}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f22}, new Term[][] {{b1, b112}, {b42}}, new Term[] {v12, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f22}, new Term[][] {{b12, b11}, {b42}}, new Term[] {v12, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b4}}, new Term[] {v12, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v1, v22}));
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> slv.defineFunsRec(
-                new Term[] {f12, f22}, new Term[][] {{b12, b112}, {b42}}, new Term[] {v12, v2}));
-  }
-
-  @Test void defineFunsRecWrongLogic() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_BV");
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
-    Sort funSort2 = d_solver.mkFunctionSort(uSort, d_solver.getIntegerSort());
-    Term b = d_solver.mkVar(bvSort, "b");
-    Term u = d_solver.mkVar(uSort, "u");
-    Term v1 = d_solver.mkConst(bvSort, "v1");
-    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
-    Term f1 = d_solver.mkConst(funSort1, "f1");
-    Term f2 = d_solver.mkConst(funSort2, "f2");
-    assertThrows(CVC5ApiException.class,
-        ()
-            -> d_solver.defineFunsRec(
-                new Term[] {f1, f2}, new Term[][] {{b, b}, {u}}, new Term[] {v1, v2}));
-  }
-
-  @Test void defineFunsRecGlobal() throws CVC5ApiException
-  {
-    Sort bSort = d_solver.getBooleanSort();
-    Sort fSort = d_solver.mkFunctionSort(bSort, bSort);
-
-    d_solver.push();
-    Term bTrue = d_solver.mkBoolean(true);
-    Term b = d_solver.mkVar(bSort, "b");
-    Term gSym = d_solver.mkConst(fSort, "g");
-    // (define-funs-rec ((g ((b Bool)) Bool)) (b))
-    d_solver.defineFunsRec(new Term[] {gSym}, new Term[][] {{b}}, new Term[] {b}, true);
-
-    // (assert (not (g true)))
-    d_solver.assertFormula(d_solver.mkTerm(APPLY_UF, gSym, bTrue).notTerm());
-    assertTrue(d_solver.checkSat().isUnsat());
-    d_solver.pop();
-    // (assert (not (g true)))
-    d_solver.assertFormula(d_solver.mkTerm(APPLY_UF, gSym, bTrue).notTerm());
-    assertTrue(d_solver.checkSat().isUnsat());
-  }
-
-  @Test void uFIteration()
-  {
-    Sort intSort = d_solver.getIntegerSort();
-    Sort funSort = d_solver.mkFunctionSort(new Sort[] {intSort, intSort}, intSort);
-    Term x = d_solver.mkConst(intSort, "x");
-    Term y = d_solver.mkConst(intSort, "y");
-    Term f = d_solver.mkConst(funSort, "f");
-    Term fxy = d_solver.mkTerm(APPLY_UF, f, x, y);
-
-    // Expecting the uninterpreted function to be one of the children
-    Term expected_children[] = new Term[] {f, x, y};
-    int idx = 0;
-    for (Term c : fxy)
-    {
-      assertEquals(c, expected_children[idx]);
-      idx++;
-    }
-  }
-
-  @Test void getInfo()
-  {
-    assertDoesNotThrow(() -> d_solver.getInfo("name"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.getInfo("asdf"));
-  }
-
-  @Test void getInterpolant() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_LIA");
-    d_solver.setOption("produce-interpols", "default");
-    d_solver.setOption("incremental", "false");
-
-    Sort intSort = d_solver.getIntegerSort();
-    Term zero = d_solver.mkInteger(0);
-    Term x = d_solver.mkConst(intSort, "x");
-    Term y = d_solver.mkConst(intSort, "y");
-    Term z = d_solver.mkConst(intSort, "z");
-
-    // Assumptions for interpolation: x + y > 0 /\ x < 0
-    d_solver.assertFormula(d_solver.mkTerm(GT, d_solver.mkTerm(PLUS, x, y), zero));
-    d_solver.assertFormula(d_solver.mkTerm(LT, x, zero));
-    // Conjecture for interpolation: y + z > 0 \/ z < 0
-    Term conj = d_solver.mkTerm(
-        OR, d_solver.mkTerm(GT, d_solver.mkTerm(PLUS, y, z), zero), d_solver.mkTerm(LT, z, zero));
-    Term output = d_solver.getNullTerm();
-    // Call the interpolation api, while the resulting interpolant is the output
-    d_solver.getInterpolant(conj, output);
-
-    // We expect the resulting output to be a boolean formula
-    assertTrue(output.getSort().isBoolean());
-  }
-
-  @Test void getOp() throws CVC5ApiException
-  {
-    Sort bv32 = d_solver.mkBitVectorSort(32);
-    Term a = d_solver.mkConst(bv32, "a");
-    Op ext = d_solver.mkOp(BITVECTOR_EXTRACT, 2, 1);
-    Term exta = d_solver.mkTerm(ext, a);
-
-    assertFalse(a.hasOp());
-    assertThrows(CVC5ApiException.class, () -> a.getOp());
-    assertTrue(exta.hasOp());
-    assertEquals(exta.getOp(), ext);
-
-    // Test Datatypes -- more complicated
-    DatatypeDecl consListSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    cons.addSelectorSelf("tail");
-    consListSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    consListSpec.addConstructor(nil);
-    Sort consListSort = d_solver.mkDatatypeSort(consListSpec);
-    Datatype consList = consListSort.getDatatype();
-
-    Term consTerm = consList.getConstructorTerm("cons");
-    Term nilTerm = consList.getConstructorTerm("nil");
-    Term headTerm = consList.getConstructor("cons").getSelectorTerm("head");
-
-    Term listnil = d_solver.mkTerm(APPLY_CONSTRUCTOR, nilTerm);
-    Term listcons1 = d_solver.mkTerm(APPLY_CONSTRUCTOR, consTerm, d_solver.mkInteger(1), listnil);
-    Term listhead = d_solver.mkTerm(APPLY_SELECTOR, headTerm, listcons1);
-
-    assertTrue(listnil.hasOp());
-    assertTrue(listcons1.hasOp());
-    assertTrue(listhead.hasOp());
-  }
-
-  @Test void getOption()
-  {
-    assertDoesNotThrow(() -> d_solver.getOption("incremental"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.getOption("asdf"));
-  }
-
-  @Test void getOptionNames()
-  {
-    String[] names = d_solver.getOptionNames();
-    assertTrue(names.length > 100);
-    assertTrue(Arrays.asList(names).contains("verbose"));
-    assertFalse(Arrays.asList(names).contains("foobar"));
-  }
-
-  @Test void getOptionInfo()
-  {
-    List<Executable> assertions = new ArrayList<>();
-    {
-      assertions.add(
-          () -> assertThrows(CVC5ApiException.class, () -> d_solver.getOptionInfo("asdf-invalid")));
-    }
-    {
-      OptionInfo info = d_solver.getOptionInfo("verbose");
-      assertions.add(() -> assertEquals("verbose", info.getName()));
-      assertions.add(
-          () -> assertEquals(Arrays.asList(new String[] {}), Arrays.asList(info.getAliases())));
-      assertions.add(() -> assertTrue(info.getBaseInfo() instanceof OptionInfo.VoidInfo));
-    }
-    {
-      // int64 type with default
-      OptionInfo info = d_solver.getOptionInfo("verbosity");
-      assertions.add(() -> assertEquals("verbosity", info.getName()));
-      assertions.add(
-          () -> assertEquals(Arrays.asList(new String[] {}), Arrays.asList(info.getAliases())));
-      assertions.add(
-          () -> assertTrue(info.getBaseInfo().getClass() == OptionInfo.NumberInfo.class));
-      OptionInfo.NumberInfo<BigInteger> numInfo =
-          (OptionInfo.NumberInfo<BigInteger>) info.getBaseInfo();
-      assertions.add(() -> assertEquals(0, numInfo.getDefaultValue().intValue()));
-      assertions.add(() -> assertEquals(0, numInfo.getCurrentValue().intValue()));
-      assertions.add(
-          () -> assertFalse(numInfo.getMinimum() != null || numInfo.getMaximum() != null));
-      assertions.add(() -> assertEquals(info.intValue().intValue(), 0));
-    }
-    assertAll(assertions);
-    {
-      OptionInfo info = d_solver.getOptionInfo("random-freq");
-      assertEquals(info.getName(), "random-freq");
-      assertEquals(
-          Arrays.asList(info.getAliases()), Arrays.asList(new String[] {"random-frequency"}));
-      assertTrue(info.getBaseInfo().getClass() == OptionInfo.NumberInfo.class);
-      OptionInfo.NumberInfo<Double> ni = (OptionInfo.NumberInfo<Double>) info.getBaseInfo();
-      assertEquals(ni.getCurrentValue(), 0.0);
-      assertEquals(ni.getDefaultValue(), 0.0);
-      assertTrue(ni.getMinimum() != null && ni.getMaximum() != null);
-      assertEquals(ni.getMinimum(), 0.0);
-      assertEquals(ni.getMaximum(), 1.0);
-      assertEquals(info.doubleValue(), 0.0);
-    }
-    {
-      // mode option
-      OptionInfo info = d_solver.getOptionInfo("output");
-      assertions.clear();
-      assertions.add(() -> assertEquals("output", info.getName()));
-      assertions.add(
-          () -> assertEquals(Arrays.asList(new String[] {}), Arrays.asList(info.getAliases())));
-      assertions.add(() -> assertTrue(info.getBaseInfo().getClass() == OptionInfo.ModeInfo.class));
-      OptionInfo.ModeInfo modeInfo = (OptionInfo.ModeInfo) info.getBaseInfo();
-      assertions.add(() -> assertEquals("NONE", modeInfo.getDefaultValue()));
-      assertions.add(() -> assertEquals("OutputTag::NONE", modeInfo.getCurrentValue()));
-      assertions.add(() -> assertTrue(Arrays.asList(modeInfo.getModes()).contains("NONE")));
-    }
-    assertAll(assertions);
-  }
-
-  @Test void getUnsatAssumptions1()
-  {
-    d_solver.setOption("incremental", "false");
-    d_solver.checkSatAssuming(d_solver.mkFalse());
-    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatAssumptions());
-  }
-
-  @Test void getUnsatAssumptions2()
-  {
-    d_solver.setOption("incremental", "true");
-    d_solver.setOption("produce-unsat-assumptions", "false");
-    d_solver.checkSatAssuming(d_solver.mkFalse());
-    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatAssumptions());
-  }
-
-  @Test void getUnsatAssumptions3()
-  {
-    d_solver.setOption("incremental", "true");
-    d_solver.setOption("produce-unsat-assumptions", "true");
-    d_solver.checkSatAssuming(d_solver.mkFalse());
-    assertDoesNotThrow(() -> d_solver.getUnsatAssumptions());
-    d_solver.checkSatAssuming(d_solver.mkTrue());
-    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatAssumptions());
-  }
-
-  @Test void getUnsatCore1()
-  {
-    d_solver.setOption("incremental", "false");
-    d_solver.assertFormula(d_solver.mkFalse());
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatCore());
-  }
-
-  @Test void getUnsatCore2()
-  {
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-unsat-cores", "false");
-    d_solver.assertFormula(d_solver.mkFalse());
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getUnsatCore());
-  }
-
-  @Test void getUnsatCoreAndProof()
-  {
-    d_solver.setOption("incremental", "true");
-    d_solver.setOption("produce-unsat-cores", "true");
-    d_solver.setOption("produce-proofs", "true");
-
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
-    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    Term f = d_solver.mkConst(uToIntSort, "f");
-    Term p = d_solver.mkConst(intPredSort, "p");
-    Term zero = d_solver.mkInteger(0);
-    Term one = d_solver.mkInteger(1);
-    Term f_x = d_solver.mkTerm(Kind.APPLY_UF, f, x);
-    Term f_y = d_solver.mkTerm(Kind.APPLY_UF, f, y);
-    Term sum = d_solver.mkTerm(Kind.PLUS, f_x, f_y);
-    Term p_0 = d_solver.mkTerm(Kind.APPLY_UF, p, zero);
-    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
-    d_solver.assertFormula(d_solver.mkTerm(Kind.GT, zero, f_x));
-    d_solver.assertFormula(d_solver.mkTerm(Kind.GT, zero, f_y));
-    d_solver.assertFormula(d_solver.mkTerm(Kind.GT, sum, one));
-    d_solver.assertFormula(p_0);
-    d_solver.assertFormula(p_f_y.notTerm());
-    assertTrue(d_solver.checkSat().isUnsat());
-
-    Term[] unsat_core = d_solver.getUnsatCore();
-
-    assertDoesNotThrow(() -> d_solver.getProof());
-
-    d_solver.resetAssertions();
-    for (Term t : unsat_core)
-    {
-      d_solver.assertFormula(t);
-    }
-    Result res = d_solver.checkSat();
-    assertTrue(res.isUnsat());
-    assertDoesNotThrow(() -> d_solver.getProof());
-  }
-
-  @Test void getDifficulty()
-  {
-    d_solver.setOption("produce-difficulty", "true");
-    // cannot ask before a check sat
-    assertThrows(CVC5ApiException.class, () -> d_solver.getDifficulty());
-    d_solver.checkSat();
-    assertDoesNotThrow(() -> d_solver.getDifficulty());
-  }
-
-  @Test void getDifficulty2()
-  {
-    d_solver.checkSat();
-    // option is not set
-    assertThrows(CVC5ApiException.class, () -> d_solver.getDifficulty());
-  }
-
-  @Test void getDifficulty3() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-difficulty", "true");
-    Sort intSort = d_solver.getIntegerSort();
-    Term x = d_solver.mkConst(intSort, "x");
-    Term zero = d_solver.mkInteger(0);
-    Term ten = d_solver.mkInteger(10);
-    Term f0 = d_solver.mkTerm(GEQ, x, ten);
-    Term f1 = d_solver.mkTerm(GEQ, zero, x);
-    d_solver.checkSat();
-    Map<Term, Term> dmap = d_solver.getDifficulty();
-    // difficulty should map assertions to integer values
-    for (Map.Entry<Term, Term> t : dmap.entrySet())
-    {
-      assertTrue(t.getKey() == f0 || t.getKey() == f1);
-      assertTrue(t.getValue().getKind() == Kind.CONST_RATIONAL);
-    }
-  }
-
-  @Test void getValue1()
-  {
-    d_solver.setOption("produce-models", "false");
-    Term t = d_solver.mkTrue();
-    d_solver.assertFormula(t);
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getValue(t));
-  }
-
-  @Test void getValue2()
-  {
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkFalse();
-    d_solver.assertFormula(t);
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getValue(t));
-  }
-
-  @Test void getValue3()
-  {
-    d_solver.setOption("produce-models", "true");
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
-    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
-    Term[] unsat_core;
-
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    Term z = d_solver.mkConst(uSort, "z");
-    Term f = d_solver.mkConst(uToIntSort, "f");
-    Term p = d_solver.mkConst(intPredSort, "p");
-    Term zero = d_solver.mkInteger(0);
-    Term one = d_solver.mkInteger(1);
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
-
-    d_solver.assertFormula(d_solver.mkTerm(LEQ, zero, f_x));
-    d_solver.assertFormula(d_solver.mkTerm(LEQ, zero, f_y));
-    d_solver.assertFormula(d_solver.mkTerm(LEQ, sum, one));
-    d_solver.assertFormula(p_0.notTerm());
-    d_solver.assertFormula(p_f_y);
-    assertTrue(d_solver.checkSat().isSat());
-    assertDoesNotThrow(() -> d_solver.getValue(x));
-    assertDoesNotThrow(() -> d_solver.getValue(y));
-    assertDoesNotThrow(() -> d_solver.getValue(z));
-    assertDoesNotThrow(() -> d_solver.getValue(sum));
-    assertDoesNotThrow(() -> d_solver.getValue(p_f_y));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.getValue(x));
-  }
-
-  @Test void getModelDomainElements()
-  {
-    d_solver.setOption("produce-models", "true");
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort intSort = d_solver.getIntegerSort();
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    Term z = d_solver.mkConst(uSort, "z");
-    Term f = d_solver.mkTerm(DISTINCT, x, y, z);
-    d_solver.assertFormula(f);
-    d_solver.checkSat();
-    assertDoesNotThrow(() -> d_solver.getModelDomainElements(uSort));
-    assertTrue(d_solver.getModelDomainElements(uSort).length >= 3);
-    assertThrows(CVC5ApiException.class, () -> d_solver.getModelDomainElements(intSort));
-  }
-
-  @Test void getModelDomainElements2()
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("finite-model-find", "true");
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkVar(uSort, "x");
-    Term y = d_solver.mkVar(uSort, "y");
-    Term eq = d_solver.mkTerm(EQUAL, x, y);
-    Term bvl = d_solver.mkTerm(BOUND_VAR_LIST, x, y);
-    Term f = d_solver.mkTerm(FORALL, bvl, eq);
-    d_solver.assertFormula(f);
-    d_solver.checkSat();
-    assertDoesNotThrow(() -> d_solver.getModelDomainElements(uSort));
-    // a model for the above must interpret u as size 1
-    assertTrue(d_solver.getModelDomainElements(uSort).length == 1);
-  }
-
-  @Test void isModelCoreSymbol()
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("model-cores", "simple");
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    Term z = d_solver.mkConst(uSort, "z");
-    Term zero = d_solver.mkInteger(0);
-    Term f = d_solver.mkTerm(NOT, d_solver.mkTerm(EQUAL, x, y));
-    d_solver.assertFormula(f);
-    d_solver.checkSat();
-    assertTrue(d_solver.isModelCoreSymbol(x));
-    assertTrue(d_solver.isModelCoreSymbol(y));
-    assertFalse(d_solver.isModelCoreSymbol(z));
-    assertThrows(CVC5ApiException.class, () -> d_solver.isModelCoreSymbol(zero));
-  }
-
-  @Test void getModel()
-  {
-    d_solver.setOption("produce-models", "true");
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    Term z = d_solver.mkConst(uSort, "z");
-    Term f = d_solver.mkTerm(NOT, d_solver.mkTerm(EQUAL, x, y));
-    d_solver.assertFormula(f);
-    d_solver.checkSat();
-    Sort[] sorts = new Sort[] {uSort};
-    Term[] terms = new Term[] {x, y};
-    assertDoesNotThrow(() -> d_solver.getModel(sorts, terms));
-    Term nullTerm = d_solver.getNullTerm();
-    Term[] terms2 = new Term[] {x, y, nullTerm};
-    assertThrows(CVC5ApiException.class, () -> d_solver.getModel(sorts, terms2));
-  }
-
-  @Test void getModel2()
-  {
-    d_solver.setOption("produce-models", "true");
-    Sort[] sorts = new Sort[] {};
-    Term[] terms = new Term[] {};
-    assertThrows(CVC5ApiException.class, () -> d_solver.getModel(sorts, terms));
-  }
-
-  @Test void getModel3()
-  {
-    d_solver.setOption("produce-models", "true");
-    Sort[] sorts = new Sort[] {};
-    final Term[] terms = new Term[] {};
-    d_solver.checkSat();
-    assertDoesNotThrow(() -> d_solver.getModel(sorts, terms));
-    Sort integer = d_solver.getIntegerSort();
-    Sort[] sorts2 = new Sort[] {integer};
-    assertThrows(CVC5ApiException.class, () -> d_solver.getModel(sorts2, terms));
-  }
-
-  @Test void getQuantifierElimination()
-  {
-    Term x = d_solver.mkVar(d_solver.getBooleanSort(), "x");
-    Term forall = d_solver.mkTerm(FORALL,
-        d_solver.mkTerm(BOUND_VAR_LIST, x),
-        d_solver.mkTerm(OR, x, d_solver.mkTerm(NOT, x)));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.getQuantifierElimination(d_solver.getNullTerm()));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.getQuantifierElimination(new Solver().mkBoolean(false)));
-
-    assertDoesNotThrow(() -> d_solver.getQuantifierElimination(forall));
-  }
-
-  @Test void getQuantifierEliminationDisjunct()
-  {
-    Term x = d_solver.mkVar(d_solver.getBooleanSort(), "x");
-    Term forall = d_solver.mkTerm(FORALL,
-        d_solver.mkTerm(BOUND_VAR_LIST, x),
-        d_solver.mkTerm(OR, x, d_solver.mkTerm(NOT, x)));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.getQuantifierEliminationDisjunct(d_solver.getNullTerm()));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.getQuantifierEliminationDisjunct(new Solver().mkBoolean(false)));
-
-    assertDoesNotThrow(() -> d_solver.getQuantifierEliminationDisjunct(forall));
-  }
-
-  @Test void declareSeparationHeap() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    Sort integer = d_solver.getIntegerSort();
-    assertDoesNotThrow(() -> d_solver.declareSeparationHeap(integer, integer));
-    // cannot declare separation logic heap more than once
-    assertThrows(CVC5ApiException.class, () -> d_solver.declareSeparationHeap(integer, integer));
-  }
-
-  /**
-   * Helper function for testGetSeparation{Heap,Nil}TermX. Asserts and checks
-   * some simple separation logic constraints.
-   */
-
-  void checkSimpleSeparationConstraints(Solver solver)
-  {
-    Sort integer = solver.getIntegerSort();
-    // declare the separation heap
-    solver.declareSeparationHeap(integer, integer);
-    Term x = solver.mkConst(integer, "x");
-    Term p = solver.mkConst(integer, "p");
-    Term heap = solver.mkTerm(SEP_PTO, p, x);
-    solver.assertFormula(heap);
-    Term nil = solver.mkSepNil(integer);
-    solver.assertFormula(nil.eqTerm(solver.mkReal(5)));
-    solver.checkSat();
-  }
-
-  @Test void getSeparationHeapTerm1() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_BV");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkTrue();
-    d_solver.assertFormula(t);
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
-  }
-
-  @Test void getSeparationHeapTerm2() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "false");
-    checkSimpleSeparationConstraints(d_solver);
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
-  }
-
-  @Test void getSeparationHeapTerm3() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkFalse();
-    d_solver.assertFormula(t);
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
-  }
-
-  @Test void getSeparationHeapTerm4() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkTrue();
-    d_solver.assertFormula(t);
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationHeap());
-  }
-
-  @Test void getSeparationHeapTerm5() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    checkSimpleSeparationConstraints(d_solver);
-    assertDoesNotThrow(() -> d_solver.getSeparationHeap());
-  }
-
-  @Test void getSeparationNilTerm1() throws CVC5ApiException
-  {
-    d_solver.setLogic("QF_BV");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkTrue();
-    d_solver.assertFormula(t);
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
-  }
-
-  @Test void getSeparationNilTerm2() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "false");
-    checkSimpleSeparationConstraints(d_solver);
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
-  }
-
-  @Test void getSeparationNilTerm3() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkFalse();
-    d_solver.assertFormula(t);
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
-  }
-
-  @Test void getSeparationNilTerm4() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    Term t = d_solver.mkTrue();
-    d_solver.assertFormula(t);
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSeparationNilTerm());
-  }
-
-  @Test void getSeparationNilTerm5() throws CVC5ApiException
-  {
-    d_solver.setLogic("ALL");
-    d_solver.setOption("incremental", "false");
-    d_solver.setOption("produce-models", "true");
-    checkSimpleSeparationConstraints(d_solver);
-    assertDoesNotThrow(() -> d_solver.getSeparationNilTerm());
-  }
-
-  @Test void push1()
-  {
-    d_solver.setOption("incremental", "true");
-    assertDoesNotThrow(() -> d_solver.push(1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("incremental", "false"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("incremental", "true"));
-  }
-
-  @Test void push2()
-  {
-    d_solver.setOption("incremental", "false");
-    assertThrows(CVC5ApiException.class, () -> d_solver.push(1));
-  }
-
-  @Test void pop1()
-  {
-    d_solver.setOption("incremental", "false");
-    assertThrows(CVC5ApiException.class, () -> d_solver.pop(1));
-  }
-
-  @Test void pop2()
-  {
-    d_solver.setOption("incremental", "true");
-    assertThrows(CVC5ApiException.class, () -> d_solver.pop(1));
-  }
-
-  @Test void pop3()
-  {
-    d_solver.setOption("incremental", "true");
-    assertDoesNotThrow(() -> d_solver.push(1));
-    assertDoesNotThrow(() -> d_solver.pop(1));
-    assertThrows(CVC5ApiException.class, () -> d_solver.pop(1));
-  }
-
-  @Test void blockModel1()
-  {
-    d_solver.setOption("produce-models", "true");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModel());
-  }
-
-  @Test void blockModel2() throws CVC5ApiException
-  {
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModel());
-  }
-
-  @Test void blockModel3() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModel());
-  }
-
-  @Test void blockModel4() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertDoesNotThrow(() -> d_solver.blockModel());
-  }
-
-  @Test void blockModelValues1() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {}));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.blockModelValues(new Term[] {d_solver.getNullTerm()}));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.blockModelValues(new Term[] {new Solver().mkBoolean(false)}));
-  }
-
-  @Test void blockModelValues2() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {x}));
-  }
-
-  @Test void blockModelValues3() throws CVC5ApiException
-  {
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {x}));
-  }
-
-  @Test void blockModelValues4() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> d_solver.blockModelValues(new Term[] {x}));
-  }
-
-  @Test void blockModelValues5() throws CVC5ApiException
-  {
-    d_solver.setOption("produce-models", "true");
-    d_solver.setOption("block-models", "literals");
-    Term x = d_solver.mkConst(d_solver.getBooleanSort(), "x");
-    d_solver.assertFormula(x.eqTerm(x));
-    d_solver.checkSat();
-    assertDoesNotThrow(() -> d_solver.blockModelValues(new Term[] {x}));
-  }
-
-  @Test void setInfo() throws CVC5ApiException
-  {
-    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("cvc4-lagic", "QF_BV"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("cvc2-logic", "QF_BV"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("cvc4-logic", "asdf"));
-
-    assertDoesNotThrow(() -> d_solver.setInfo("source", "asdf"));
-    assertDoesNotThrow(() -> d_solver.setInfo("category", "asdf"));
-    assertDoesNotThrow(() -> d_solver.setInfo("difficulty", "asdf"));
-    assertDoesNotThrow(() -> d_solver.setInfo("filename", "asdf"));
-    assertDoesNotThrow(() -> d_solver.setInfo("license", "asdf"));
-    assertDoesNotThrow(() -> d_solver.setInfo("name", "asdf"));
-    assertDoesNotThrow(() -> d_solver.setInfo("notes", "asdf"));
-
-    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2"));
-    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2.0"));
-    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2.5"));
-    assertDoesNotThrow(() -> d_solver.setInfo("smt-lib-version", "2.6"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("smt-lib-version", ".0"));
-
-    assertDoesNotThrow(() -> d_solver.setInfo("status", "sat"));
-    assertDoesNotThrow(() -> d_solver.setInfo("status", "unsat"));
-    assertDoesNotThrow(() -> d_solver.setInfo("status", "unknown"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setInfo("status", "asdf"));
-  }
-
-  @Test void simplify() throws CVC5ApiException
-  {
-    assertThrows(CVC5ApiException.class, () -> d_solver.simplify(d_solver.getNullTerm()));
-
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort funSort1 = d_solver.mkFunctionSort(new Sort[] {bvSort, bvSort}, bvSort);
-    Sort funSort2 = d_solver.mkFunctionSort(uSort, d_solver.getIntegerSort());
-    DatatypeDecl consListSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    cons.addSelectorSelf("tail");
-    consListSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    consListSpec.addConstructor(nil);
-    Sort consListSort = d_solver.mkDatatypeSort(consListSpec);
-
-    Term x = d_solver.mkConst(bvSort, "x");
-    assertDoesNotThrow(() -> d_solver.simplify(x));
-    Term a = d_solver.mkConst(bvSort, "a");
-    assertDoesNotThrow(() -> d_solver.simplify(a));
-    Term b = d_solver.mkConst(bvSort, "b");
-    assertDoesNotThrow(() -> d_solver.simplify(b));
-    Term x_eq_x = d_solver.mkTerm(EQUAL, x, x);
-    assertDoesNotThrow(() -> d_solver.simplify(x_eq_x));
-    assertNotEquals(d_solver.mkTrue(), x_eq_x);
-    assertEquals(d_solver.mkTrue(), d_solver.simplify(x_eq_x));
-    Term x_eq_b = d_solver.mkTerm(EQUAL, x, b);
-    assertDoesNotThrow(() -> d_solver.simplify(x_eq_b));
-    assertNotEquals(d_solver.mkTrue(), x_eq_b);
-    assertNotEquals(d_solver.mkTrue(), d_solver.simplify(x_eq_b));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.simplify(x));
-
-    Term i1 = d_solver.mkConst(d_solver.getIntegerSort(), "i1");
-    assertDoesNotThrow(() -> d_solver.simplify(i1));
-    Term i2 = d_solver.mkTerm(MULT, i1, d_solver.mkInteger("23"));
-    assertDoesNotThrow(() -> d_solver.simplify(i2));
-    assertNotEquals(i1, i2);
-    assertNotEquals(i1, d_solver.simplify(i2));
-    Term i3 = d_solver.mkTerm(PLUS, i1, d_solver.mkInteger(0));
-    assertDoesNotThrow(() -> d_solver.simplify(i3));
-    assertNotEquals(i1, i3);
-    assertEquals(i1, d_solver.simplify(i3));
-
-    Datatype consList = consListSort.getDatatype();
-    Term dt1 = d_solver.mkTerm(APPLY_CONSTRUCTOR,
-        consList.getConstructorTerm("cons"),
-        d_solver.mkInteger(0),
-        d_solver.mkTerm(APPLY_CONSTRUCTOR, consList.getConstructorTerm("nil")));
-    assertDoesNotThrow(() -> d_solver.simplify(dt1));
-    Term dt2 = d_solver.mkTerm(
-        APPLY_SELECTOR, consList.getConstructor("cons").getSelectorTerm("head"), dt1);
-    assertDoesNotThrow(() -> d_solver.simplify(dt2));
-
-    Term b1 = d_solver.mkVar(bvSort, "b1");
-    assertDoesNotThrow(() -> d_solver.simplify(b1));
-    Term b2 = d_solver.mkVar(bvSort, "b1");
-    assertDoesNotThrow(() -> d_solver.simplify(b2));
-    Term b3 = d_solver.mkVar(uSort, "b3");
-    assertDoesNotThrow(() -> d_solver.simplify(b3));
-    Term v1 = d_solver.mkConst(bvSort, "v1");
-    assertDoesNotThrow(() -> d_solver.simplify(v1));
-    Term v2 = d_solver.mkConst(d_solver.getIntegerSort(), "v2");
-    assertDoesNotThrow(() -> d_solver.simplify(v2));
-    Term f1 = d_solver.mkConst(funSort1, "f1");
-    assertDoesNotThrow(() -> d_solver.simplify(f1));
-    Term f2 = d_solver.mkConst(funSort2, "f2");
-    assertDoesNotThrow(() -> d_solver.simplify(f2));
-    d_solver.defineFunsRec(new Term[] {f1, f2}, new Term[][] {{b1, b2}, {b3}}, new Term[] {v1, v2});
-    assertDoesNotThrow(() -> d_solver.simplify(f1));
-    assertDoesNotThrow(() -> d_solver.simplify(f2));
-  }
-
-  @Test void assertFormula()
-  {
-    assertDoesNotThrow(() -> d_solver.assertFormula(d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.assertFormula(d_solver.getNullTerm()));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.assertFormula(d_solver.mkTrue()));
-  }
-
-  @Test void checkEntailed()
-  {
-    d_solver.setOption("incremental", "false");
-    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkEntailed(d_solver.mkTrue()));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.checkEntailed(d_solver.mkTrue()));
-  }
-
-  @Test void checkEntailed1()
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Term x = d_solver.mkConst(boolSort, "x");
-    Term y = d_solver.mkConst(boolSort, "y");
-    Term z = d_solver.mkTerm(AND, x, y);
-    d_solver.setOption("incremental", "true");
-    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkEntailed(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
-    assertDoesNotThrow(() -> d_solver.checkEntailed(z));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.checkEntailed(d_solver.mkTrue()));
-  }
-
-  @Test void checkEntailed2()
-  {
-    d_solver.setOption("incremental", "true");
-
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
-    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term n = d_solver.getNullTerm();
-    // Constants
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    // Functions
-    Term f = d_solver.mkConst(uToIntSort, "f");
-    Term p = d_solver.mkConst(intPredSort, "p");
-    // Values
-    Term zero = d_solver.mkInteger(0);
-    Term one = d_solver.mkInteger(1);
-    // Terms
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
-    // Assertions
-    Term assertions = d_solver.mkTerm(AND,
-        new Term[] {
-            d_solver.mkTerm(LEQ, zero, f_x), // 0 <= f(x)
-            d_solver.mkTerm(LEQ, zero, f_y), // 0 <= f(y)
-            d_solver.mkTerm(LEQ, sum, one), // f(x) + f(y) <= 1
-            p_0.notTerm(), // not p(0)
-            p_f_y // p(f(y))
-        });
-
-    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTrue()));
-    d_solver.assertFormula(assertions);
-    assertDoesNotThrow(() -> d_solver.checkEntailed(d_solver.mkTerm(DISTINCT, x, y)));
-    assertDoesNotThrow(()
-                           -> d_solver.checkEntailed(
-                               new Term[] {d_solver.mkFalse(), d_solver.mkTerm(DISTINCT, x, y)}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkEntailed(n));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.checkEntailed(new Term[] {n, d_solver.mkTerm(DISTINCT, x, y)}));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.checkEntailed(d_solver.mkTrue()));
-  }
-
-  @Test void checkSat() throws CVC5ApiException
-  {
-    d_solver.setOption("incremental", "false");
-    assertDoesNotThrow(() -> d_solver.checkSat());
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkSat());
-  }
-
-  @Test void checkSatAssuming() throws CVC5ApiException
-  {
-    d_solver.setOption("incremental", "false");
-    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkSatAssuming(d_solver.mkTrue()));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.checkSatAssuming(d_solver.mkTrue()));
-  }
-
-  @Test void checkSatAssuming1() throws CVC5ApiException
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Term x = d_solver.mkConst(boolSort, "x");
-    Term y = d_solver.mkConst(boolSort, "y");
-    Term z = d_solver.mkTerm(AND, x, y);
-    d_solver.setOption("incremental", "true");
-    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkSatAssuming(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
-    assertDoesNotThrow(() -> d_solver.checkSatAssuming(z));
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.checkSatAssuming(d_solver.mkTrue()));
-  }
-
-  @Test void checkSatAssuming2() throws CVC5ApiException
-  {
-    d_solver.setOption("incremental", "true");
-
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort uToIntSort = d_solver.mkFunctionSort(uSort, intSort);
-    Sort intPredSort = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term n = d_solver.getNullTerm();
-    // Constants
-    Term x = d_solver.mkConst(uSort, "x");
-    Term y = d_solver.mkConst(uSort, "y");
-    // Functions
-    Term f = d_solver.mkConst(uToIntSort, "f");
-    Term p = d_solver.mkConst(intPredSort, "p");
-    // Values
-    Term zero = d_solver.mkInteger(0);
-    Term one = d_solver.mkInteger(1);
-    // Terms
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
-    // Assertions
-    Term assertions = d_solver.mkTerm(AND,
-        new Term[] {
-            d_solver.mkTerm(LEQ, zero, f_x), // 0 <= f(x)
-            d_solver.mkTerm(LEQ, zero, f_y), // 0 <= f(y)
-            d_solver.mkTerm(LEQ, sum, one), // f(x) + f(y) <= 1
-            p_0.notTerm(), // not p(0)
-            p_f_y // p(f(y))
-        });
-
-    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTrue()));
-    d_solver.assertFormula(assertions);
-    assertDoesNotThrow(() -> d_solver.checkSatAssuming(d_solver.mkTerm(DISTINCT, x, y)));
-    assertDoesNotThrow(()
-                           -> d_solver.checkSatAssuming(
-                               new Term[] {d_solver.mkFalse(), d_solver.mkTerm(DISTINCT, x, y)}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.checkSatAssuming(n));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.checkSatAssuming(new Term[] {n, d_solver.mkTerm(DISTINCT, x, y)}));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.checkSatAssuming(d_solver.mkTrue()));
-  }
-
-  @Test void setLogic() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.setLogic("AUFLIRA"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setLogic("AF_BV"));
-    d_solver.assertFormula(d_solver.mkTrue());
-    assertThrows(CVC5ApiException.class, () -> d_solver.setLogic("AUFLIRA"));
-  }
-
-  @Test void setOption() throws CVC5ApiException
-  {
-    assertDoesNotThrow(() -> d_solver.setOption("bv-sat-solver", "minisat"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("bv-sat-solver", "1"));
-    d_solver.assertFormula(d_solver.mkTrue());
-    assertThrows(CVC5ApiException.class, () -> d_solver.setOption("bv-sat-solver", "minisat"));
-  }
-
-  @Test void resetAssertions() throws CVC5ApiException
-  {
-    d_solver.setOption("incremental", "true");
-
-    Sort bvSort = d_solver.mkBitVectorSort(4);
-    Term one = d_solver.mkBitVector(4, 1);
-    Term x = d_solver.mkConst(bvSort, "x");
-    Term ule = d_solver.mkTerm(BITVECTOR_ULE, x, one);
-    Term srem = d_solver.mkTerm(BITVECTOR_SREM, one, x);
-    d_solver.push(4);
-    Term slt = d_solver.mkTerm(BITVECTOR_SLT, srem, one);
-    d_solver.resetAssertions();
-    d_solver.checkSatAssuming(new Term[] {slt, ule});
-  }
-
-  @Test void mkSygusVar() throws CVC5ApiException
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort intSort = d_solver.getIntegerSort();
-    Sort funSort = d_solver.mkFunctionSort(intSort, boolSort);
-
-    assertDoesNotThrow(() -> d_solver.mkSygusVar(boolSort));
-    assertDoesNotThrow(() -> d_solver.mkSygusVar(funSort));
-    assertDoesNotThrow(() -> d_solver.mkSygusVar(boolSort, ("b")));
-    assertDoesNotThrow(() -> d_solver.mkSygusVar(funSort, ""));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkSygusVar(d_solver.getNullSort()));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkSygusVar(d_solver.getNullSort(), "a"));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.mkSygusVar(boolSort));
-  }
-
-  @Test void mkSygusGrammar() throws CVC5ApiException
-  {
-    Term nullTerm = d_solver.getNullTerm();
-    Term boolTerm = d_solver.mkBoolean(true);
-    Term boolVar = d_solver.mkVar(d_solver.getBooleanSort());
-    Term intVar = d_solver.mkVar(d_solver.getIntegerSort());
-
-    assertDoesNotThrow(() -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {intVar}));
-    assertDoesNotThrow(() -> d_solver.mkSygusGrammar(new Term[] {boolVar}, new Term[] {intVar}));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {}));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {nullTerm}));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkSygusGrammar(new Term[] {}, new Term[] {boolTerm}));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkSygusGrammar(new Term[] {boolTerm}, new Term[] {intVar}));
-
-    Solver slv = new Solver();
-    Term boolVar2 = slv.mkVar(slv.getBooleanSort());
-    Term intVar2 = slv.mkVar(slv.getIntegerSort());
-    assertDoesNotThrow(() -> slv.mkSygusGrammar(new Term[] {boolVar2}, new Term[] {intVar2}));
-
-    assertThrows(CVC5ApiException.class,
-        () -> slv.mkSygusGrammar(new Term[] {boolVar}, new Term[] {intVar2}));
-    assertThrows(CVC5ApiException.class,
-        () -> slv.mkSygusGrammar(new Term[] {boolVar2}, new Term[] {intVar}));
-  }
-
-  @Test void synthFun() throws CVC5ApiException
-  {
-    Sort nullSort = d_solver.getNullSort();
-    Sort bool = d_solver.getBooleanSort();
-    Sort integer = d_solver.getIntegerSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term x = d_solver.mkVar(bool);
-
-    Term start1 = d_solver.mkVar(bool);
-    Term start2 = d_solver.mkVar(integer);
-
-    Grammar g1 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start1});
-    g1.addRule(start1, d_solver.mkBoolean(false));
-
-    Grammar g2 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start2});
-    g2.addRule(start2, d_solver.mkInteger(0));
-
-    assertDoesNotThrow(() -> d_solver.synthFun("", new Term[] {}, bool));
-    assertDoesNotThrow(() -> d_solver.synthFun("f1", new Term[] {x}, bool));
-    assertDoesNotThrow(() -> d_solver.synthFun("f2", new Term[] {x}, bool, g1));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.synthFun("f3", new Term[] {nullTerm}, bool));
-    assertThrows(CVC5ApiException.class, () -> d_solver.synthFun("f4", new Term[] {}, nullSort));
-    assertThrows(CVC5ApiException.class, () -> d_solver.synthFun("f6", new Term[] {x}, bool, g2));
-
-    Solver slv = new Solver();
-    Term x2 = slv.mkVar(slv.getBooleanSort());
-    assertDoesNotThrow(() -> slv.synthFun("f1", new Term[] {x2}, slv.getBooleanSort()));
-
-    assertThrows(
-        CVC5ApiException.class, () -> slv.synthFun("", new Term[] {}, d_solver.getBooleanSort()));
-    assertThrows(CVC5ApiException.class,
-        () -> slv.synthFun("f1", new Term[] {x}, d_solver.getBooleanSort()));
-  }
-
-  @Test void synthInv() throws CVC5ApiException
-  {
-    Sort bool = d_solver.getBooleanSort();
-    Sort integer = d_solver.getIntegerSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term x = d_solver.mkVar(bool);
-
-    Term start1 = d_solver.mkVar(bool);
-    Term start2 = d_solver.mkVar(integer);
-
-    Grammar g1 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start1});
-    g1.addRule(start1, d_solver.mkBoolean(false));
-
-    Grammar g2 = d_solver.mkSygusGrammar(new Term[] {x}, new Term[] {start2});
-    g2.addRule(start2, d_solver.mkInteger(0));
-
-    assertDoesNotThrow(() -> d_solver.synthInv("", new Term[] {}));
-    assertDoesNotThrow(() -> d_solver.synthInv("i1", new Term[] {x}));
-    assertDoesNotThrow(() -> d_solver.synthInv("i2", new Term[] {x}, g1));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.synthInv("i3", new Term[] {nullTerm}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.synthInv("i4", new Term[] {x}, g2));
-  }
-
-  @Test void addSygusConstraint() throws CVC5ApiException
-  {
-    Term nullTerm = d_solver.getNullTerm();
-    Term boolTerm = d_solver.mkBoolean(true);
-    Term intTerm = d_solver.mkInteger(1);
-
-    assertDoesNotThrow(() -> d_solver.addSygusConstraint(boolTerm));
-    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusConstraint(nullTerm));
-    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusConstraint(intTerm));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.addSygusConstraint(boolTerm));
-  }
-
-  @Test void addSygusAssume()
-  {
-    Term nullTerm = d_solver.getNullTerm();
-    Term boolTerm = d_solver.mkBoolean(false);
-    Term intTerm = d_solver.mkInteger(1);
-
-    assertDoesNotThrow(() -> d_solver.addSygusAssume(boolTerm));
-    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusAssume(nullTerm));
-    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusAssume(intTerm));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.addSygusAssume(boolTerm));
-  }
-
-  @Test void addSygusInvConstraint() throws CVC5ApiException
-  {
-    Sort bool = d_solver.getBooleanSort();
-    Sort real = d_solver.getRealSort();
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term intTerm = d_solver.mkInteger(1);
-
-    Term inv = d_solver.declareFun("inv", new Sort[] {real}, bool);
-    Term pre = d_solver.declareFun("pre", new Sort[] {real}, bool);
-    Term trans = d_solver.declareFun("trans", new Sort[] {real, real}, bool);
-    Term post = d_solver.declareFun("post", new Sort[] {real}, bool);
-
-    Term inv1 = d_solver.declareFun("inv1", new Sort[] {real}, real);
-
-    Term trans1 = d_solver.declareFun("trans1", new Sort[] {bool, real}, bool);
-    Term trans2 = d_solver.declareFun("trans2", new Sort[] {real, bool}, bool);
-    Term trans3 = d_solver.declareFun("trans3", new Sort[] {real, real}, real);
-
-    assertDoesNotThrow(() -> d_solver.addSygusInvConstraint(inv, pre, trans, post));
-
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(nullTerm, pre, trans, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, nullTerm, trans, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, nullTerm, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans, nullTerm));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(intTerm, pre, trans, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv1, pre, trans, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, trans, trans, post));
-    assertThrows(CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, pre, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans1, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans2, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans3, post));
-    assertThrows(
-        CVC5ApiException.class, () -> d_solver.addSygusInvConstraint(inv, pre, trans, trans));
-
-    Solver slv = new Solver();
-    Sort boolean2 = slv.getBooleanSort();
-    Sort real2 = slv.getRealSort();
-    Term inv22 = slv.declareFun("inv", new Sort[] {real2}, boolean2);
-    Term pre22 = slv.declareFun("pre", new Sort[] {real2}, boolean2);
-    Term trans22 = slv.declareFun("trans", new Sort[] {real2, real2}, boolean2);
-    Term post22 = slv.declareFun("post", new Sort[] {real2}, boolean2);
-    assertDoesNotThrow(() -> slv.addSygusInvConstraint(inv22, pre22, trans22, post22));
-
-    assertThrows(
-        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv, pre22, trans22, post22));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv22, pre, trans22, post22));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv22, pre22, trans, post22));
-    assertThrows(
-        CVC5ApiException.class, () -> slv.addSygusInvConstraint(inv22, pre22, trans22, post));
-  }
-
-  @Test void getSynthSolution() throws CVC5ApiException
-  {
-    d_solver.setOption("lang", "sygus2");
-    d_solver.setOption("incremental", "false");
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term x = d_solver.mkBoolean(false);
-    Term f = d_solver.synthFun("f", new Term[] {}, d_solver.getBooleanSort());
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolution(f));
-
-    d_solver.checkSynth();
-
-    assertDoesNotThrow(() -> d_solver.getSynthSolution(f));
-    assertDoesNotThrow(() -> d_solver.getSynthSolution(f));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolution(nullTerm));
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolution(x));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.getSynthSolution(f));
-  }
-
-  @Test void getSynthSolutions() throws CVC5ApiException
-  {
-    d_solver.setOption("lang", "sygus2");
-    d_solver.setOption("incremental", "false");
-
-    Term nullTerm = d_solver.getNullTerm();
-    Term x = d_solver.mkBoolean(false);
-    Term f = d_solver.synthFun("f", new Term[] {}, d_solver.getBooleanSort());
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {f}));
-
-    d_solver.checkSynth();
-
-    assertDoesNotThrow(() -> d_solver.getSynthSolutions(new Term[] {f}));
-    assertDoesNotThrow(() -> d_solver.getSynthSolutions(new Term[] {f, f}));
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {nullTerm}));
-    assertThrows(CVC5ApiException.class, () -> d_solver.getSynthSolutions(new Term[] {x}));
-
-    Solver slv = new Solver();
-    assertThrows(CVC5ApiException.class, () -> slv.getSynthSolutions(new Term[] {x}));
-  }
-
-  @Test void tupleProject() throws CVC5ApiException
-  {
-    Sort[] sorts = new Sort[] {d_solver.getBooleanSort(),
-        d_solver.getIntegerSort(),
-        d_solver.getStringSort(),
-        d_solver.mkSetSort(d_solver.getStringSort())};
-    Term[] elements = new Term[] {d_solver.mkBoolean(true),
-        d_solver.mkInteger(3),
-        d_solver.mkString("C"),
-        d_solver.mkTerm(SINGLETON, d_solver.mkString("Z"))};
-
-    Term tuple = d_solver.mkTuple(sorts, elements);
-
-    int[] indices1 = new int[] {};
-    int[] indices2 = new int[] {0};
-    int[] indices3 = new int[] {0, 1};
-    int[] indices4 = new int[] {0, 0, 2, 2, 3, 3, 0};
-    int[] indices5 = new int[] {4};
-    int[] indices6 = new int[] {0, 4};
-
-    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices1), tuple));
-    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices2), tuple));
-    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices3), tuple));
-    assertDoesNotThrow(() -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices4), tuple));
-
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices5), tuple));
-    assertThrows(CVC5ApiException.class,
-        () -> d_solver.mkTerm(d_solver.mkOp(TUPLE_PROJECT, indices6), tuple));
-
-    int[] indices = new int[] {0, 3, 2, 0, 1, 2};
-
-    Op op = d_solver.mkOp(TUPLE_PROJECT, indices);
-    Term projection = d_solver.mkTerm(op, tuple);
-
-    Datatype datatype = tuple.getSort().getDatatype();
-    DatatypeConstructor constructor = datatype.getConstructor(0);
-
-    for (int i = 0; i < indices.length; i++)
-    {
-      Term selectorTerm = constructor.getSelector(indices[i]).getSelectorTerm();
-      Term selectedTerm = d_solver.mkTerm(APPLY_SELECTOR, selectorTerm, tuple);
-      Term simplifiedTerm = d_solver.simplify(selectedTerm);
-      assertEquals(elements[indices[i]], simplifiedTerm);
-    }
-
-    assertEquals("((_ tuple_project 0 3 2 0 1 2) (tuple true 3 \"C\" (singleton "
-            + "\"Z\")))",
-        projection.toString());
-  }
-}
diff --git a/test/unit/api/java/cvc5/SortTest.java b/test/unit/api/java/cvc5/SortTest.java
deleted file mode 100644 (file)
index 1ea7032..0000000
+++ /dev/null
@@ -1,590 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Andrew Reynolds, Mathias Preiner, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the guards of the Java API functions.
- */
-
-package cvc5;
-
-import static cvc5.Kind.*;
-import static org.junit.jupiter.api.Assertions.*;
-
-import java.math.BigInteger;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Iterator;
-import java.util.List;
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
-
-class SortTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  Sort create_datatype_sort() throws CVC5ApiException
-  {
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    cons.addSelectorSelf("tail");
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    return d_solver.mkDatatypeSort(dtypeSpec);
-  }
-
-  Sort create_param_datatype_sort() throws CVC5ApiException
-  {
-    Sort sort = d_solver.mkParamSort("T");
-    DatatypeDecl paramDtypeSpec = d_solver.mkDatatypeDecl("paramlist", sort);
-    DatatypeConstructorDecl paramCons = d_solver.mkDatatypeConstructorDecl("cons");
-    DatatypeConstructorDecl paramNil = d_solver.mkDatatypeConstructorDecl("nil");
-    paramCons.addSelector("head", sort);
-    paramDtypeSpec.addConstructor(paramCons);
-    paramDtypeSpec.addConstructor(paramNil);
-    return d_solver.mkDatatypeSort(paramDtypeSpec);
-  }
-
-  @Test void operators_comparison()
-  {
-    assertDoesNotThrow(() -> d_solver.getIntegerSort() == d_solver.getNullSort());
-    assertDoesNotThrow(() -> d_solver.getIntegerSort() != d_solver.getNullSort());
-    assertDoesNotThrow(() -> d_solver.getIntegerSort().compareTo(d_solver.getNullSort()));
-  }
-
-  @Test void isBoolean()
-  {
-    assertTrue(d_solver.getBooleanSort().isBoolean());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isBoolean());
-  }
-
-  @Test void isInteger()
-  {
-    assertTrue(d_solver.getIntegerSort().isInteger());
-    assertTrue(!d_solver.getRealSort().isInteger());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isInteger());
-  }
-
-  @Test void isReal()
-  {
-    assertTrue(d_solver.getRealSort().isReal());
-    assertTrue(!d_solver.getIntegerSort().isReal());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isReal());
-  }
-
-  @Test void isString()
-  {
-    assertTrue(d_solver.getStringSort().isString());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isString());
-  }
-
-  @Test void isRegExp()
-  {
-    assertTrue(d_solver.getRegExpSort().isRegExp());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isRegExp());
-  }
-
-  @Test void isRoundingMode() throws CVC5ApiException
-  {
-    assertTrue(d_solver.getRoundingModeSort().isRoundingMode());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isRoundingMode());
-  }
-
-  @Test void isBitVector() throws CVC5ApiException
-  {
-    assertTrue(d_solver.mkBitVectorSort(8).isBitVector());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isBitVector());
-  }
-
-  @Test void isFloatingPoint() throws CVC5ApiException
-  {
-    assertTrue(d_solver.mkFloatingPointSort(8, 24).isFloatingPoint());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isFloatingPoint());
-  }
-
-  @Test void isDatatype() throws CVC5ApiException
-  {
-    Sort dt_sort = create_datatype_sort();
-    assertTrue(dt_sort.isDatatype());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isDatatype());
-  }
-
-  @Test void isParametricDatatype() throws CVC5ApiException
-  {
-    Sort param_dt_sort = create_param_datatype_sort();
-    assertTrue(param_dt_sort.isParametricDatatype());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isParametricDatatype());
-  }
-
-  @Test void isConstructor() throws CVC5ApiException
-  {
-    Sort dt_sort = create_datatype_sort();
-    Datatype dt = dt_sort.getDatatype();
-    Sort cons_sort = dt.getConstructor(0).getConstructorTerm().getSort();
-    assertTrue(cons_sort.isConstructor());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isConstructor());
-  }
-
-  @Test void isSelector() throws CVC5ApiException
-  {
-    Sort dt_sort = create_datatype_sort();
-    Datatype dt = dt_sort.getDatatype();
-    Sort cons_sort = dt.getConstructor(0).getSelector(1).getSelectorTerm().getSort();
-    assertTrue(cons_sort.isSelector());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isSelector());
-  }
-
-  @Test void isTester() throws CVC5ApiException
-  {
-    Sort dt_sort = create_datatype_sort();
-    Datatype dt = dt_sort.getDatatype();
-    Sort cons_sort = dt.getConstructor(0).getTesterTerm().getSort();
-    assertTrue(cons_sort.isTester());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isTester());
-  }
-
-  @Test void isFunction()
-  {
-    Sort fun_sort = d_solver.mkFunctionSort(d_solver.getRealSort(), d_solver.getIntegerSort());
-    assertTrue(fun_sort.isFunction());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isFunction());
-  }
-
-  @Test void isPredicate()
-  {
-    Sort pred_sort = d_solver.mkPredicateSort(new Sort[] {d_solver.getRealSort()});
-    assertTrue(pred_sort.isPredicate());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isPredicate());
-  }
-
-  @Test void isTuple()
-  {
-    Sort tup_sort = d_solver.mkTupleSort(new Sort[] {d_solver.getRealSort()});
-    assertTrue(tup_sort.isTuple());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isTuple());
-  }
-
-  @Test void isRecord()
-  {
-    Sort rec_sort =
-        d_solver.mkRecordSort(new Pair[] {new Pair<String, Sort>("asdf", d_solver.getRealSort())});
-    assertTrue(rec_sort.isRecord());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isRecord());
-  }
-
-  @Test void isArray()
-  {
-    Sort arr_sort = d_solver.mkArraySort(d_solver.getRealSort(), d_solver.getIntegerSort());
-    assertTrue(arr_sort.isArray());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isArray());
-  }
-
-  @Test void isSet()
-  {
-    Sort set_sort = d_solver.mkSetSort(d_solver.getRealSort());
-    assertTrue(set_sort.isSet());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isSet());
-  }
-
-  @Test void isBag()
-  {
-    Sort bag_sort = d_solver.mkBagSort(d_solver.getRealSort());
-    assertTrue(bag_sort.isBag());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isBag());
-  }
-
-  @Test void isSequence()
-  {
-    Sort seq_sort = d_solver.mkSequenceSort(d_solver.getRealSort());
-    assertTrue(seq_sort.isSequence());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isSequence());
-  }
-
-  @Test void isUninterpreted()
-  {
-    Sort un_sort = d_solver.mkUninterpretedSort("asdf");
-    assertTrue(un_sort.isUninterpretedSort());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isUninterpretedSort());
-  }
-
-  @Test void isSortConstructor() throws CVC5ApiException
-  {
-    Sort sc_sort = d_solver.mkSortConstructorSort("asdf", 1);
-    assertTrue(sc_sort.isSortConstructor());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isSortConstructor());
-  }
-
-  @Test void isFirstClass()
-  {
-    Sort fun_sort = d_solver.mkFunctionSort(d_solver.getRealSort(), d_solver.getIntegerSort());
-    assertTrue(d_solver.getIntegerSort().isFirstClass());
-    assertTrue(fun_sort.isFirstClass());
-    Sort reSort = d_solver.getRegExpSort();
-    assertFalse(reSort.isFirstClass());
-    assertDoesNotThrow(() -> d_solver.getNullSort().isFirstClass());
-  }
-
-  @Test void isFunctionLike() throws CVC5ApiException
-  {
-    Sort fun_sort = d_solver.mkFunctionSort(d_solver.getRealSort(), d_solver.getIntegerSort());
-    assertFalse(d_solver.getIntegerSort().isFunctionLike());
-    assertTrue(fun_sort.isFunctionLike());
-
-    Sort dt_sort = create_datatype_sort();
-    Datatype dt = dt_sort.getDatatype();
-    Sort cons_sort = dt.getConstructor(0).getSelector(1).getSelectorTerm().getSort();
-    assertTrue(cons_sort.isFunctionLike());
-
-    assertDoesNotThrow(() -> d_solver.getNullSort().isFunctionLike());
-  }
-
-  @Test void isSubsortOf()
-  {
-    assertTrue(d_solver.getIntegerSort().isSubsortOf(d_solver.getIntegerSort()));
-    assertTrue(d_solver.getIntegerSort().isSubsortOf(d_solver.getRealSort()));
-    assertFalse(d_solver.getIntegerSort().isSubsortOf(d_solver.getBooleanSort()));
-    assertDoesNotThrow(() -> d_solver.getNullSort().isSubsortOf(d_solver.getNullSort()));
-  }
-
-  @Test void isComparableTo()
-  {
-    assertTrue(d_solver.getIntegerSort().isComparableTo(d_solver.getIntegerSort()));
-    assertTrue(d_solver.getIntegerSort().isComparableTo(d_solver.getRealSort()));
-    assertFalse(d_solver.getIntegerSort().isComparableTo(d_solver.getBooleanSort()));
-    assertDoesNotThrow(() -> d_solver.getNullSort().isComparableTo(d_solver.getNullSort()));
-  }
-
-  @Test void getDatatype() throws CVC5ApiException
-  {
-    Sort dtypeSort = create_datatype_sort();
-    assertDoesNotThrow(() -> dtypeSort.getDatatype());
-    // create bv sort, check should fail
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getDatatype());
-  }
-
-  @Test void datatypeSorts() throws CVC5ApiException
-  {
-    Sort intSort = d_solver.getIntegerSort();
-    Sort dtypeSort = create_datatype_sort();
-    Datatype dt = dtypeSort.getDatatype();
-    assertFalse(dtypeSort.isConstructor());
-    assertThrows(CVC5ApiException.class, () -> dtypeSort.getConstructorCodomainSort());
-    assertThrows(CVC5ApiException.class, () -> dtypeSort.getConstructorDomainSorts());
-    assertThrows(CVC5ApiException.class, () -> dtypeSort.getConstructorArity());
-
-    // get constructor
-    DatatypeConstructor dcons = dt.getConstructor(0);
-    Term consTerm = dcons.getConstructorTerm();
-    Sort consSort = consTerm.getSort();
-    assertTrue(consSort.isConstructor());
-    assertFalse(consSort.isTester());
-    assertFalse(consSort.isSelector());
-    assertEquals(consSort.getConstructorArity(), 2);
-    Sort[] consDomSorts = consSort.getConstructorDomainSorts();
-    assertEquals(consDomSorts[0], intSort);
-    assertEquals(consDomSorts[1], dtypeSort);
-    assertEquals(consSort.getConstructorCodomainSort(), dtypeSort);
-
-    // get tester
-    Term isConsTerm = dcons.getTesterTerm();
-    assertTrue(isConsTerm.getSort().isTester());
-    assertEquals(isConsTerm.getSort().getTesterDomainSort(), dtypeSort);
-    Sort booleanSort = d_solver.getBooleanSort();
-    assertEquals(isConsTerm.getSort().getTesterCodomainSort(), booleanSort);
-    assertThrows(CVC5ApiException.class, () -> booleanSort.getTesterDomainSort());
-    assertThrows(CVC5ApiException.class, () -> booleanSort.getTesterCodomainSort());
-
-    // get selector
-    DatatypeSelector dselTail = dcons.getSelector(1);
-    Term tailTerm = dselTail.getSelectorTerm();
-    assertTrue(tailTerm.getSort().isSelector());
-    assertEquals(tailTerm.getSort().getSelectorDomainSort(), dtypeSort);
-    assertEquals(tailTerm.getSort().getSelectorCodomainSort(), dtypeSort);
-    assertThrows(CVC5ApiException.class, () -> booleanSort.getSelectorDomainSort());
-    assertThrows(CVC5ApiException.class, () -> booleanSort.getSelectorCodomainSort());
-  }
-
-  @Test void instantiate() throws CVC5ApiException
-  {
-    // instantiate parametric datatype, check should not fail
-    Sort paramDtypeSort = create_param_datatype_sort();
-    assertDoesNotThrow(() -> paramDtypeSort.instantiate(new Sort[] {d_solver.getIntegerSort()}));
-    // instantiate non-parametric datatype sort, check should fail
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
-    assertThrows(CVC5ApiException.class,
-        () -> dtypeSort.instantiate(new Sort[] {d_solver.getIntegerSort()}));
-  }
-
-  @Test void getFunctionArity() throws CVC5ApiException
-  {
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    assertDoesNotThrow(() -> funSort.getFunctionArity());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getFunctionArity());
-  }
-
-  @Test void getFunctionDomainSorts() throws CVC5ApiException
-  {
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    assertDoesNotThrow(() -> funSort.getFunctionDomainSorts());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getFunctionDomainSorts());
-  }
-
-  @Test void getFunctionCodomainSort() throws CVC5ApiException
-  {
-    Sort funSort =
-        d_solver.mkFunctionSort(d_solver.mkUninterpretedSort("u"), d_solver.getIntegerSort());
-    assertDoesNotThrow(() -> funSort.getFunctionCodomainSort());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getFunctionCodomainSort());
-  }
-
-  @Test void getArrayIndexSort() throws CVC5ApiException
-  {
-    Sort elementSort = d_solver.mkBitVectorSort(32);
-    Sort indexSort = d_solver.mkBitVectorSort(32);
-    Sort arraySort = d_solver.mkArraySort(indexSort, elementSort);
-    assertDoesNotThrow(() -> arraySort.getArrayIndexSort());
-    assertThrows(CVC5ApiException.class, () -> indexSort.getArrayIndexSort());
-  }
-
-  @Test void getArrayElementSort() throws CVC5ApiException
-  {
-    Sort elementSort = d_solver.mkBitVectorSort(32);
-    Sort indexSort = d_solver.mkBitVectorSort(32);
-    Sort arraySort = d_solver.mkArraySort(indexSort, elementSort);
-    assertDoesNotThrow(() -> arraySort.getArrayElementSort());
-    assertThrows(CVC5ApiException.class, () -> indexSort.getArrayElementSort());
-  }
-
-  @Test void getSetElementSort() throws CVC5ApiException
-  {
-    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
-    assertDoesNotThrow(() -> setSort.getSetElementSort());
-    Sort elementSort = setSort.getSetElementSort();
-    assertEquals(elementSort, d_solver.getIntegerSort());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getSetElementSort());
-  }
-
-  @Test void getBagElementSort() throws CVC5ApiException
-  {
-    Sort bagSort = d_solver.mkBagSort(d_solver.getIntegerSort());
-    assertDoesNotThrow(() -> bagSort.getBagElementSort());
-    Sort elementSort = bagSort.getBagElementSort();
-    assertEquals(elementSort, d_solver.getIntegerSort());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getBagElementSort());
-  }
-
-  @Test void getSequenceElementSort() throws CVC5ApiException
-  {
-    Sort seqSort = d_solver.mkSequenceSort(d_solver.getIntegerSort());
-    assertTrue(seqSort.isSequence());
-    assertDoesNotThrow(() -> seqSort.getSequenceElementSort());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertFalse(bvSort.isSequence());
-    assertThrows(CVC5ApiException.class, () -> bvSort.getSequenceElementSort());
-  }
-
-  @Test void getUninterpretedSortName() throws CVC5ApiException
-  {
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    assertDoesNotThrow(() -> uSort.getUninterpretedSortName());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getUninterpretedSortName());
-  }
-
-  @Test void isUninterpretedSortParameterized() throws CVC5ApiException
-  {
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    assertFalse(uSort.isUninterpretedSortParameterized());
-    Sort sSort = d_solver.mkSortConstructorSort("s", 1);
-    Sort siSort = sSort.instantiate(new Sort[] {uSort});
-    assertTrue(siSort.isUninterpretedSortParameterized());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.isUninterpretedSortParameterized());
-  }
-
-  @Test void getUninterpretedSortParamSorts() throws CVC5ApiException
-  {
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    assertDoesNotThrow(() -> uSort.getUninterpretedSortParamSorts());
-    Sort sSort = d_solver.mkSortConstructorSort("s", 2);
-    Sort siSort = sSort.instantiate(new Sort[] {uSort, uSort});
-    assertEquals(siSort.getUninterpretedSortParamSorts().length, 2);
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getUninterpretedSortParamSorts());
-  }
-
-  @Test void getUninterpretedSortConstructorName() throws CVC5ApiException
-  {
-    Sort sSort = d_solver.mkSortConstructorSort("s", 2);
-    assertDoesNotThrow(() -> sSort.getSortConstructorName());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getSortConstructorName());
-  }
-
-  @Test void getUninterpretedSortConstructorArity() throws CVC5ApiException
-  {
-    Sort sSort = d_solver.mkSortConstructorSort("s", 2);
-    assertDoesNotThrow(() -> sSort.getSortConstructorArity());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getSortConstructorArity());
-  }
-
-  @Test void getBitVectorSize() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertDoesNotThrow(() -> bvSort.getBitVectorSize());
-    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
-    assertThrows(CVC5ApiException.class, () -> setSort.getBitVectorSize());
-  }
-
-  @Test void getFloatingPointExponentSize() throws CVC5ApiException
-  {
-    Sort fpSort = d_solver.mkFloatingPointSort(4, 8);
-    assertDoesNotThrow(() -> fpSort.getFloatingPointExponentSize());
-    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
-    assertThrows(CVC5ApiException.class, () -> setSort.getFloatingPointExponentSize());
-  }
-
-  @Test void getFloatingPointSignificandSize() throws CVC5ApiException
-  {
-    Sort fpSort = d_solver.mkFloatingPointSort(4, 8);
-    assertDoesNotThrow(() -> fpSort.getFloatingPointSignificandSize());
-    Sort setSort = d_solver.mkSetSort(d_solver.getIntegerSort());
-    assertThrows(CVC5ApiException.class, () -> setSort.getFloatingPointSignificandSize());
-  }
-
-  @Test void getDatatypeParamSorts() throws CVC5ApiException
-  {
-    // create parametric datatype, check should not fail
-    Sort sort = d_solver.mkParamSort("T");
-    DatatypeDecl paramDtypeSpec = d_solver.mkDatatypeDecl("paramlist", sort);
-    DatatypeConstructorDecl paramCons = d_solver.mkDatatypeConstructorDecl("cons");
-    DatatypeConstructorDecl paramNil = d_solver.mkDatatypeConstructorDecl("nil");
-    paramCons.addSelector("head", sort);
-    paramDtypeSpec.addConstructor(paramCons);
-    paramDtypeSpec.addConstructor(paramNil);
-    Sort paramDtypeSort = d_solver.mkDatatypeSort(paramDtypeSpec);
-    assertDoesNotThrow(() -> paramDtypeSort.getDatatypeParamSorts());
-    // create non-parametric datatype sort, check should fail
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
-    assertThrows(CVC5ApiException.class, () -> dtypeSort.getDatatypeParamSorts());
-  }
-
-  @Test void getDatatypeArity() throws CVC5ApiException
-  {
-    // create datatype sort, check should not fail
-    DatatypeDecl dtypeSpec = d_solver.mkDatatypeDecl("list");
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    cons.addSelector("head", d_solver.getIntegerSort());
-    dtypeSpec.addConstructor(cons);
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    dtypeSpec.addConstructor(nil);
-    Sort dtypeSort = d_solver.mkDatatypeSort(dtypeSpec);
-    assertDoesNotThrow(() -> dtypeSort.getDatatypeArity());
-    // create bv sort, check should fail
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getDatatypeArity());
-  }
-
-  @Test void getTupleLength() throws CVC5ApiException
-  {
-    Sort tupleSort =
-        d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort(), d_solver.getIntegerSort()});
-    assertDoesNotThrow(() -> tupleSort.getTupleLength());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getTupleLength());
-  }
-
-  @Test void getTupleSorts() throws CVC5ApiException
-  {
-    Sort tupleSort =
-        d_solver.mkTupleSort(new Sort[] {d_solver.getIntegerSort(), d_solver.getIntegerSort()});
-    assertDoesNotThrow(() -> tupleSort.getTupleSorts());
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    assertThrows(CVC5ApiException.class, () -> bvSort.getTupleSorts());
-  }
-
-  @Test void sortCompare() throws CVC5ApiException
-  {
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort intSort = d_solver.getIntegerSort();
-    Sort bvSort = d_solver.mkBitVectorSort(32);
-    Sort bvSort2 = d_solver.mkBitVectorSort(32);
-    assertTrue(bvSort.compareTo(bvSort2) >= 0);
-    assertTrue(bvSort.compareTo(bvSort2) <= 0);
-    assertTrue(intSort.compareTo(boolSort) > 0 != intSort.compareTo(boolSort) < 0);
-    assertTrue((intSort.compareTo(bvSort) > 0 || intSort.equals(bvSort))
-        == (intSort.compareTo(bvSort) >= 0));
-  }
-
-  @Test void sortSubtyping()
-  {
-    Sort intSort = d_solver.getIntegerSort();
-    Sort realSort = d_solver.getRealSort();
-    assertTrue(intSort.isSubsortOf(realSort));
-    assertFalse(realSort.isSubsortOf(intSort));
-    assertTrue(intSort.isComparableTo(realSort));
-    assertTrue(realSort.isComparableTo(intSort));
-
-    Sort arraySortII = d_solver.mkArraySort(intSort, intSort);
-    Sort arraySortIR = d_solver.mkArraySort(intSort, realSort);
-    assertFalse(arraySortII.isComparableTo(intSort));
-    // we do not support subtyping for arrays
-    assertFalse(arraySortII.isComparableTo(arraySortIR));
-
-    Sort setSortI = d_solver.mkSetSort(intSort);
-    Sort setSortR = d_solver.mkSetSort(realSort);
-    // we don't support subtyping for sets
-    assertFalse(setSortI.isComparableTo(setSortR));
-    assertFalse(setSortI.isSubsortOf(setSortR));
-    assertFalse(setSortR.isComparableTo(setSortI));
-    assertFalse(setSortR.isSubsortOf(setSortI));
-  }
-
-  @Test void sortScopedToString() throws CVC5ApiException
-  {
-    String name = "uninterp-sort";
-    Sort bvsort8 = d_solver.mkBitVectorSort(8);
-    Sort uninterp_sort = d_solver.mkUninterpretedSort(name);
-    assertEquals(bvsort8.toString(), "(_ BitVec 8)");
-    assertEquals(uninterp_sort.toString(), name);
-    Solver solver2;
-    assertEquals(bvsort8.toString(), "(_ BitVec 8)");
-    assertEquals(uninterp_sort.toString(), name);
-  }
-}
diff --git a/test/unit/api/java/cvc5/TermTest.java b/test/unit/api/java/cvc5/TermTest.java
deleted file mode 100644 (file)
index 98f6680..0000000
+++ /dev/null
@@ -1,1059 +0,0 @@
-/******************************************************************************
- * Top contributors (to current version):
- *   Aina Niemetz, Makai Mann, Andrew Reynolds, Mudathir Mohamed
- *
- * This file is part of the cvc5 project.
- *
- * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
- * in the top-level source directory and their institutional affiliations.
- * All rights reserved.  See the file COPYING in the top-level source
- * directory for licensing information.
- * ****************************************************************************
- *
- * Black box testing of the Term class.
- */
-
-package cvc5;
-
-import static cvc5.Kind.*;
-import static org.junit.jupiter.api.Assertions.*;
-
-import java.math.BigInteger;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Set;
-import java.util.stream.Collectors;
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
-
-class TermTest
-{
-  private Solver d_solver;
-
-  @BeforeEach void setUp()
-  {
-    d_solver = new Solver();
-  }
-
-  @Test void eq()
-  {
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Term x = d_solver.mkVar(uSort, "x");
-    Term y = d_solver.mkVar(uSort, "y");
-    Term z = d_solver.getNullTerm();
-
-    assertTrue(x == x);
-    assertFalse(x != x);
-    assertFalse(x == y);
-    assertTrue(x != y);
-    assertFalse((x == z));
-    assertTrue(x != z);
-  }
-
-  @Test void getId()
-  {
-    Term n = d_solver.getNullTerm();
-    assertThrows(CVC5ApiException.class, () -> n.getId());
-    Term x = d_solver.mkVar(d_solver.getIntegerSort(), "x");
-    assertDoesNotThrow(() -> x.getId());
-    Term y = x;
-    assertEquals(x.getId(), y.getId());
-
-    Term z = d_solver.mkVar(d_solver.getIntegerSort(), "z");
-    assertNotEquals(x.getId(), z.getId());
-  }
-
-  @Test void getKind() throws CVC5ApiException
-  {
-    Sort uSort = d_solver.mkUninterpretedSort("u");
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(uSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term n = d_solver.getNullTerm();
-    assertThrows(CVC5ApiException.class, () -> n.getKind());
-    Term x = d_solver.mkVar(uSort, "x");
-    assertDoesNotThrow(() -> x.getKind());
-    Term y = d_solver.mkVar(uSort, "y");
-    assertDoesNotThrow(() -> y.getKind());
-
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertDoesNotThrow(() -> f.getKind());
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertDoesNotThrow(() -> p.getKind());
-
-    Term zero = d_solver.mkInteger(0);
-    assertDoesNotThrow(() -> zero.getKind());
-
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertDoesNotThrow(() -> f_x.getKind());
-    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
-    assertDoesNotThrow(() -> f_y.getKind());
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
-    assertDoesNotThrow(() -> sum.getKind());
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.getKind());
-    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
-    assertDoesNotThrow(() -> p_f_y.getKind());
-
-    // Sequence kinds do not exist internally, test that the API properly
-    // converts them back.
-    Sort seqSort = d_solver.mkSequenceSort(intSort);
-    Term s = d_solver.mkConst(seqSort, "s");
-    Term ss = d_solver.mkTerm(SEQ_CONCAT, s, s);
-    assertEquals(ss.getKind(), SEQ_CONCAT);
-  }
-
-  @Test void getSort() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term n = d_solver.getNullTerm();
-    assertThrows(CVC5ApiException.class, () -> n.getSort());
-    Term x = d_solver.mkVar(bvSort, "x");
-    assertDoesNotThrow(() -> x.getSort());
-    assertEquals(x.getSort(), bvSort);
-    Term y = d_solver.mkVar(bvSort, "y");
-    assertDoesNotThrow(() -> y.getSort());
-    assertEquals(y.getSort(), bvSort);
-
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertDoesNotThrow(() -> f.getSort());
-    assertEquals(f.getSort(), funSort1);
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertDoesNotThrow(() -> p.getSort());
-    assertEquals(p.getSort(), funSort2);
-
-    Term zero = d_solver.mkInteger(0);
-    assertDoesNotThrow(() -> zero.getSort());
-    assertEquals(zero.getSort(), intSort);
-
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertDoesNotThrow(() -> f_x.getSort());
-    assertEquals(f_x.getSort(), intSort);
-    Term f_y = d_solver.mkTerm(APPLY_UF, f, y);
-    assertDoesNotThrow(() -> f_y.getSort());
-    assertEquals(f_y.getSort(), intSort);
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_y);
-    assertDoesNotThrow(() -> sum.getSort());
-    assertEquals(sum.getSort(), intSort);
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.getSort());
-    assertEquals(p_0.getSort(), boolSort);
-    Term p_f_y = d_solver.mkTerm(APPLY_UF, p, f_y);
-    assertDoesNotThrow(() -> p_f_y.getSort());
-    assertEquals(p_f_y.getSort(), boolSort);
-  }
-
-  @Test void getOp() throws CVC5ApiException
-  {
-    Sort intsort = d_solver.getIntegerSort();
-    Sort bvsort = d_solver.mkBitVectorSort(8);
-    Sort arrsort = d_solver.mkArraySort(bvsort, intsort);
-    Sort funsort = d_solver.mkFunctionSort(intsort, bvsort);
-
-    Term x = d_solver.mkConst(intsort, "x");
-    Term a = d_solver.mkConst(arrsort, "a");
-    Term b = d_solver.mkConst(bvsort, "b");
-
-    assertFalse(x.hasOp());
-    assertThrows(CVC5ApiException.class, () -> x.getOp());
-
-    Term ab = d_solver.mkTerm(SELECT, a, b);
-    Op ext = d_solver.mkOp(BITVECTOR_EXTRACT, 4, 0);
-    Term extb = d_solver.mkTerm(ext, b);
-
-    assertTrue(ab.hasOp());
-    assertFalse(ab.getOp().isIndexed());
-    // can compare directly to a Kind (will invoke Op constructor)
-    assertTrue(extb.hasOp());
-    assertTrue(extb.getOp().isIndexed());
-    assertEquals(extb.getOp(), ext);
-
-    Term f = d_solver.mkConst(funsort, "f");
-    Term fx = d_solver.mkTerm(APPLY_UF, f, x);
-
-    assertFalse(f.hasOp());
-    assertThrows(CVC5ApiException.class, () -> f.getOp());
-    assertTrue(fx.hasOp());
-    List<Term> children = new ArrayList();
-
-    Iterator<Term> iterator = fx.iterator();
-    for (Term t : fx)
-    {
-      children.add(t);
-    }
-
-    // testing rebuild from op and children
-    assertEquals(fx, d_solver.mkTerm(fx.getOp(), children));
-
-    // Test Datatypes Ops
-    Sort sort = d_solver.mkParamSort("T");
-    DatatypeDecl listDecl = d_solver.mkDatatypeDecl("paramlist", sort);
-    DatatypeConstructorDecl cons = d_solver.mkDatatypeConstructorDecl("cons");
-    DatatypeConstructorDecl nil = d_solver.mkDatatypeConstructorDecl("nil");
-    cons.addSelector("head", sort);
-    cons.addSelectorSelf("tail");
-    listDecl.addConstructor(cons);
-    listDecl.addConstructor(nil);
-    Sort listSort = d_solver.mkDatatypeSort(listDecl);
-    Sort intListSort = listSort.instantiate(new Sort[] {d_solver.getIntegerSort()});
-    Term c = d_solver.mkConst(intListSort, "c");
-    Datatype list = listSort.getDatatype();
-    // list datatype constructor and selector operator terms
-    Term consOpTerm = list.getConstructorTerm("cons");
-    Term nilOpTerm = list.getConstructorTerm("nil");
-  }
-
-  @Test void isNull() throws CVC5ApiException
-  {
-    Term x = d_solver.getNullTerm();
-    assertTrue(x.isNull());
-    x = d_solver.mkVar(d_solver.mkBitVectorSort(4), "x");
-    assertFalse(x.isNull());
-  }
-
-  @Test void notTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().notTerm());
-    Term b = d_solver.mkTrue();
-    assertDoesNotThrow(() -> b.notTerm());
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertThrows(CVC5ApiException.class, () -> x.notTerm());
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.notTerm());
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.notTerm());
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.notTerm());
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.notTerm());
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.notTerm());
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.notTerm());
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.notTerm());
-  }
-
-  @Test void andTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term b = d_solver.mkTrue();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> b.andTerm(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> b.andTerm(b));
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertThrows(CVC5ApiException.class, () -> x.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> x.andTerm(x));
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f.andTerm(f));
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p.andTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p.andTerm(p));
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> zero.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> zero.andTerm(f));
-    assertThrows(CVC5ApiException.class, () -> zero.andTerm(p));
-    assertThrows(CVC5ApiException.class, () -> zero.andTerm(zero));
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(f));
-    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(p));
-    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> f_x.andTerm(f_x));
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(f));
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(p));
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> sum.andTerm(sum));
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_0.andTerm(sum));
-    assertDoesNotThrow(() -> p_0.andTerm(p_0));
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.andTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.andTerm(sum));
-    assertDoesNotThrow(() -> p_f_x.andTerm(p_0));
-    assertDoesNotThrow(() -> p_f_x.andTerm(p_f_x));
-  }
-
-  @Test void orTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term b = d_solver.mkTrue();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> b.orTerm(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> b.orTerm(b));
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertThrows(CVC5ApiException.class, () -> x.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> x.orTerm(x));
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f.orTerm(f));
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p.orTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p.orTerm(p));
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> zero.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> zero.orTerm(f));
-    assertThrows(CVC5ApiException.class, () -> zero.orTerm(p));
-    assertThrows(CVC5ApiException.class, () -> zero.orTerm(zero));
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(f));
-    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(p));
-    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> f_x.orTerm(f_x));
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(f));
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(p));
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> sum.orTerm(sum));
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_0.orTerm(sum));
-    assertDoesNotThrow(() -> p_0.orTerm(p_0));
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.orTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.orTerm(sum));
-    assertDoesNotThrow(() -> p_f_x.orTerm(p_0));
-    assertDoesNotThrow(() -> p_f_x.orTerm(p_f_x));
-  }
-
-  @Test void xorTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term b = d_solver.mkTrue();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> b.xorTerm(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> b.xorTerm(b));
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertThrows(CVC5ApiException.class, () -> x.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> x.xorTerm(x));
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f.xorTerm(f));
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p.xorTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p.xorTerm(p));
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(f));
-    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(p));
-    assertThrows(CVC5ApiException.class, () -> zero.xorTerm(zero));
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(f));
-    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(p));
-    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> f_x.xorTerm(f_x));
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(f));
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(p));
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> sum.xorTerm(sum));
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_0.xorTerm(sum));
-    assertDoesNotThrow(() -> p_0.xorTerm(p_0));
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.xorTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.xorTerm(sum));
-    assertDoesNotThrow(() -> p_f_x.xorTerm(p_0));
-    assertDoesNotThrow(() -> p_f_x.xorTerm(p_f_x));
-  }
-
-  @Test void eqTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term b = d_solver.mkTrue();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> b.eqTerm(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> b.eqTerm(b));
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertThrows(CVC5ApiException.class, () -> x.eqTerm(b));
-    assertDoesNotThrow(() -> x.eqTerm(x));
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f.eqTerm(x));
-    assertDoesNotThrow(() -> f.eqTerm(f));
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p.eqTerm(f));
-    assertDoesNotThrow(() -> p.eqTerm(p));
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(f));
-    assertThrows(CVC5ApiException.class, () -> zero.eqTerm(p));
-    assertDoesNotThrow(() -> zero.eqTerm(zero));
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(f));
-    assertThrows(CVC5ApiException.class, () -> f_x.eqTerm(p));
-    assertDoesNotThrow(() -> f_x.eqTerm(zero));
-    assertDoesNotThrow(() -> f_x.eqTerm(f_x));
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(f));
-    assertThrows(CVC5ApiException.class, () -> sum.eqTerm(p));
-    assertDoesNotThrow(() -> sum.eqTerm(zero));
-    assertDoesNotThrow(() -> sum.eqTerm(f_x));
-    assertDoesNotThrow(() -> sum.eqTerm(sum));
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_0.eqTerm(sum));
-    assertDoesNotThrow(() -> p_0.eqTerm(p_0));
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.eqTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.eqTerm(sum));
-    assertDoesNotThrow(() -> p_f_x.eqTerm(p_0));
-    assertDoesNotThrow(() -> p_f_x.eqTerm(p_f_x));
-  }
-
-  @Test void impTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term b = d_solver.mkTrue();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> b.impTerm(d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> b.impTerm(b));
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertThrows(CVC5ApiException.class, () -> x.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> x.impTerm(x));
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f.impTerm(f));
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p.impTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p.impTerm(p));
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> zero.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> zero.impTerm(f));
-    assertThrows(CVC5ApiException.class, () -> zero.impTerm(p));
-    assertThrows(CVC5ApiException.class, () -> zero.impTerm(zero));
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(f));
-    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(p));
-    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> f_x.impTerm(f_x));
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(f));
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(p));
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> sum.impTerm(sum));
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_0.impTerm(sum));
-    assertDoesNotThrow(() -> p_0.impTerm(p_0));
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.impTerm(b));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(f));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(p));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(zero));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(f_x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.impTerm(sum));
-    assertDoesNotThrow(() -> p_f_x.impTerm(p_0));
-    assertDoesNotThrow(() -> p_f_x.impTerm(p_f_x));
-  }
-
-  @Test void iteTerm() throws CVC5ApiException
-  {
-    Sort bvSort = d_solver.mkBitVectorSort(8);
-    Sort intSort = d_solver.getIntegerSort();
-    Sort boolSort = d_solver.getBooleanSort();
-    Sort funSort1 = d_solver.mkFunctionSort(bvSort, intSort);
-    Sort funSort2 = d_solver.mkFunctionSort(intSort, boolSort);
-
-    Term b = d_solver.mkTrue();
-    assertThrows(CVC5ApiException.class, () -> d_solver.getNullTerm().iteTerm(b, b));
-    assertThrows(CVC5ApiException.class, () -> b.iteTerm(d_solver.getNullTerm(), b));
-    assertThrows(CVC5ApiException.class, () -> b.iteTerm(b, d_solver.getNullTerm()));
-    assertDoesNotThrow(() -> b.iteTerm(b, b));
-    Term x = d_solver.mkVar(d_solver.mkBitVectorSort(8), "x");
-    assertDoesNotThrow(() -> b.iteTerm(x, x));
-    assertDoesNotThrow(() -> b.iteTerm(b, b));
-    assertThrows(CVC5ApiException.class, () -> b.iteTerm(x, b));
-    assertThrows(CVC5ApiException.class, () -> x.iteTerm(x, x));
-    assertThrows(CVC5ApiException.class, () -> x.iteTerm(x, b));
-    Term f = d_solver.mkVar(funSort1, "f");
-    assertThrows(CVC5ApiException.class, () -> f.iteTerm(b, b));
-    assertThrows(CVC5ApiException.class, () -> x.iteTerm(b, x));
-    Term p = d_solver.mkVar(funSort2, "p");
-    assertThrows(CVC5ApiException.class, () -> p.iteTerm(b, b));
-    assertThrows(CVC5ApiException.class, () -> p.iteTerm(x, b));
-    Term zero = d_solver.mkInteger(0);
-    assertThrows(CVC5ApiException.class, () -> zero.iteTerm(x, x));
-    assertThrows(CVC5ApiException.class, () -> zero.iteTerm(x, b));
-    Term f_x = d_solver.mkTerm(APPLY_UF, f, x);
-    assertThrows(CVC5ApiException.class, () -> f_x.iteTerm(b, b));
-    assertThrows(CVC5ApiException.class, () -> f_x.iteTerm(b, x));
-    Term sum = d_solver.mkTerm(PLUS, f_x, f_x);
-    assertThrows(CVC5ApiException.class, () -> sum.iteTerm(x, x));
-    assertThrows(CVC5ApiException.class, () -> sum.iteTerm(b, x));
-    Term p_0 = d_solver.mkTerm(APPLY_UF, p, zero);
-    assertDoesNotThrow(() -> p_0.iteTerm(b, b));
-    assertDoesNotThrow(() -> p_0.iteTerm(x, x));
-    assertThrows(CVC5ApiException.class, () -> p_0.iteTerm(x, b));
-    Term p_f_x = d_solver.mkTerm(APPLY_UF, p, f_x);
-    assertDoesNotThrow(() -> p_f_x.iteTerm(b, b));
-    assertDoesNotThrow(() -> p_f_x.iteTerm(x, x));
-    assertThrows(CVC5ApiException.class, () -> p_f_x.iteTerm(x, b));
-  }
-
-  @Test void termAssignment()
-  {
-    Term t1 = d_solver.mkInteger(1);
-    Term t2 = t1;
-    t2 = d_solver.mkInteger(2);
-    assertEquals(t1, d_solver.mkInteger(1));
-  }
-
-  @Test void termCompare()
-  {
-    Term t1 = d_solver.mkInteger(1);
-    Term t2 = d_solver.mkTerm(PLUS, d_solver.mkInteger(2), d_solver.mkInteger(2));
-    Term t3 = d_solver.mkTerm(PLUS, d_solver.mkInteger(2), d_solver.mkInteger(2));
-    assertTrue(t2.compareTo(t3) >= 0);
-    assertTrue(t2.compareTo(t3) <= 0);
-    assertTrue((t1.compareTo(t2) > 0) != (t1.compareTo(t2) < 0));
-    assertTrue((t1.compareTo(t2) > 0 || t1.equals(t2)) == (t1.compareTo(t2) >= 0));
-  }
-
-  @Test void termChildren() throws CVC5ApiException
-  {
-    // simple term 2+3
-    Term two = d_solver.mkInteger(2);
-    Term t1 = d_solver.mkTerm(PLUS, two, d_solver.mkInteger(3));
-    assertEquals(t1.getChild(0), two);
-    assertEquals(t1.getNumChildren(), 2);
-    Term tnull = d_solver.getNullTerm();
-    assertThrows(CVC5ApiException.class, () -> tnull.getNumChildren());
-
-    // apply term f(2)
-    Sort intSort = d_solver.getIntegerSort();
-    Sort fsort = d_solver.mkFunctionSort(intSort, intSort);
-    Term f = d_solver.mkConst(fsort, "f");
-    Term t2 = d_solver.mkTerm(APPLY_UF, f, two);
-    // due to our higher-order view of terms, we treat f as a child of APPLY_UF
-    assertEquals(t2.getNumChildren(), 2);
-    assertEquals(t2.getChild(0), f);
-    assertEquals(t2.getChild(1), two);
-    assertThrows(CVC5ApiException.class, () -> tnull.getChild(0));
-  }
-
-  @Test void getIntegerValue() throws CVC5ApiException
-  {
-    Term int1 = d_solver.mkInteger("-18446744073709551616");
-    Term int2 = d_solver.mkInteger("-18446744073709551615");
-    Term int3 = d_solver.mkInteger("-4294967296");
-    Term int4 = d_solver.mkInteger("-4294967295");
-    Term int5 = d_solver.mkInteger("-10");
-    Term int6 = d_solver.mkInteger("0");
-    Term int7 = d_solver.mkInteger("10");
-    Term int8 = d_solver.mkInteger("4294967295");
-    Term int9 = d_solver.mkInteger("4294967296");
-    Term int10 = d_solver.mkInteger("18446744073709551615");
-    Term int11 = d_solver.mkInteger("18446744073709551616");
-    Term int12 = d_solver.mkInteger("-0");
-
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger(""));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-1-"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("0.0"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-0.1"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("012"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("0000"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-01"));
-    assertThrows(CVC5ApiException.class, () -> d_solver.mkInteger("-00"));
-
-    assertTrue(int1.isIntegerValue());
-    assertEquals(int1.getIntegerValue().toString(), "-18446744073709551616");
-    assertTrue(int2.isIntegerValue());
-    assertEquals(int2.getIntegerValue().toString(), "-18446744073709551615");
-    assertTrue(int3.isIntegerValue());
-    assertEquals(int3.getIntegerValue().longValue(), -4294967296L);
-    assertEquals(int3.getIntegerValue().toString(), "-4294967296");
-    assertTrue(int4.isIntegerValue());
-    assertEquals(int4.getIntegerValue().longValue(), -4294967295L);
-    assertEquals(int4.getIntegerValue().toString(), "-4294967295");
-    assertTrue(int5.isIntegerValue());
-    assertEquals(int5.getIntegerValue().intValue(), -10);
-    assertEquals(int5.getIntegerValue().intValue(), -10);
-    assertEquals(int5.getIntegerValue().toString(), "-10");
-    assertTrue(int6.isIntegerValue());
-    assertEquals(int6.getIntegerValue().intValue(), 0);
-    assertEquals(int6.getIntegerValue().intValue(), 0);
-    assertEquals(int6.getIntegerValue().toString(), "0");
-    assertTrue(int7.isIntegerValue());
-    assertEquals(int7.getIntegerValue().intValue(), 10);
-    assertEquals(int7.getIntegerValue().intValue(), 10);
-    assertEquals(int7.getIntegerValue().toString(), "10");
-    assertTrue(int8.isIntegerValue());
-    assertEquals(int8.getIntegerValue().longValue(), 4294967295L);
-    assertEquals(int8.getIntegerValue().toString(), "4294967295");
-    assertTrue(int9.isIntegerValue());
-    assertEquals(int9.getIntegerValue().longValue(), 4294967296L);
-    assertEquals(int9.getIntegerValue().toString(), "4294967296");
-    assertTrue(int10.isIntegerValue());
-
-    assertEquals(int10.getIntegerValue().toString(), "18446744073709551615");
-    assertTrue(int11.isIntegerValue());
-    assertEquals(int11.getIntegerValue().toString(), "18446744073709551616");
-  }
-
-  @Test void getString()
-  {
-    Term s1 = d_solver.mkString("abcde");
-    assertTrue(s1.isStringValue());
-    assertEquals(s1.getStringValue(), "abcde");
-  }
-
-  @Test void getReal() throws CVC5ApiException
-  {
-    Term real1 = d_solver.mkReal("0");
-    Term real2 = d_solver.mkReal(".0");
-    Term real3 = d_solver.mkReal("-17");
-    Term real4 = d_solver.mkReal("-3/5");
-    Term real5 = d_solver.mkReal("12.7");
-    Term real6 = d_solver.mkReal("1/4294967297");
-    Term real7 = d_solver.mkReal("4294967297");
-    Term real8 = d_solver.mkReal("1/18446744073709551617");
-    Term real9 = d_solver.mkReal("18446744073709551617");
-    Term real10 = d_solver.mkReal("2343.2343");
-
-    assertTrue(real1.isRealValue());
-    assertTrue(real2.isRealValue());
-    assertTrue(real3.isRealValue());
-    assertTrue(real4.isRealValue());
-    assertTrue(real5.isRealValue());
-    assertTrue(real6.isRealValue());
-    assertTrue(real7.isRealValue());
-    assertTrue(real8.isRealValue());
-    assertTrue(real9.isRealValue());
-    assertTrue(real10.isRealValue());
-
-    assertEquals("0/1", Utils.getRational(real1.getRealValue()));
-    assertEquals("0/1", Utils.getRational(real2.getRealValue()));
-    assertEquals("-17/1", Utils.getRational(real3.getRealValue()));
-    assertEquals("-3/5", Utils.getRational(real4.getRealValue()));
-    assertEquals("127/10", Utils.getRational(real5.getRealValue()));
-    assertEquals("1/4294967297", Utils.getRational(real6.getRealValue()));
-    assertEquals("4294967297/1", Utils.getRational(real7.getRealValue()));
-    assertEquals("1/18446744073709551617", Utils.getRational(real8.getRealValue()));
-    assertEquals("18446744073709551617/1", Utils.getRational(real9.getRealValue()));
-    assertEquals("23432343/10000", Utils.getRational(real10.getRealValue()));
-  }
-
-  @Test void getConstArrayBase()
-  {
-    Sort intsort = d_solver.getIntegerSort();
-    Sort arrsort = d_solver.mkArraySort(intsort, intsort);
-    Term one = d_solver.mkInteger(1);
-    Term constarr = d_solver.mkConstArray(arrsort, one);
-
-    assertTrue(constarr.isConstArray());
-    assertEquals(one, constarr.getConstArrayBase());
-  }
-
-  @Test void getBoolean()
-  {
-    Term b1 = d_solver.mkBoolean(true);
-    Term b2 = d_solver.mkBoolean(false);
-
-    assertTrue(b1.isBooleanValue());
-    assertTrue(b2.isBooleanValue());
-    assertTrue(b1.getBooleanValue());
-    assertFalse(b2.getBooleanValue());
-  }
-
-  @Test void getBitVector() throws CVC5ApiException
-  {
-    Term b1 = d_solver.mkBitVector(8, 15);
-    Term b2 = d_solver.mkBitVector(8, "00001111", 2);
-    Term b3 = d_solver.mkBitVector(8, "15", 10);
-    Term b4 = d_solver.mkBitVector(8, "0f", 16);
-    Term b5 = d_solver.mkBitVector(9, "00001111", 2);
-    Term b6 = d_solver.mkBitVector(9, "15", 10);
-    Term b7 = d_solver.mkBitVector(9, "0f", 16);
-
-    assertTrue(b1.isBitVectorValue());
-    assertTrue(b2.isBitVectorValue());
-    assertTrue(b3.isBitVectorValue());
-    assertTrue(b4.isBitVectorValue());
-    assertTrue(b5.isBitVectorValue());
-    assertTrue(b6.isBitVectorValue());
-    assertTrue(b7.isBitVectorValue());
-
-    assertEquals("00001111", b1.getBitVectorValue(2));
-    assertEquals("15", b1.getBitVectorValue(10));
-    assertEquals("f", b1.getBitVectorValue(16));
-    assertEquals("00001111", b2.getBitVectorValue(2));
-    assertEquals("15", b2.getBitVectorValue(10));
-    assertEquals("f", b2.getBitVectorValue(16));
-    assertEquals("00001111", b3.getBitVectorValue(2));
-    assertEquals("15", b3.getBitVectorValue(10));
-    assertEquals("f", b3.getBitVectorValue(16));
-    assertEquals("00001111", b4.getBitVectorValue(2));
-    assertEquals("15", b4.getBitVectorValue(10));
-    assertEquals("f", b4.getBitVectorValue(16));
-    assertEquals("000001111", b5.getBitVectorValue(2));
-    assertEquals("15", b5.getBitVectorValue(10));
-    assertEquals("f", b5.getBitVectorValue(16));
-    assertEquals("000001111", b6.getBitVectorValue(2));
-    assertEquals("15", b6.getBitVectorValue(10));
-    assertEquals("f", b6.getBitVectorValue(16));
-    assertEquals("000001111", b7.getBitVectorValue(2));
-    assertEquals("15", b7.getBitVectorValue(10));
-    assertEquals("f", b7.getBitVectorValue(16));
-  }
-
-  @Test void getAbstractValue() throws CVC5ApiException
-  {
-    Term v1 = d_solver.mkAbstractValue(1);
-    Term v2 = d_solver.mkAbstractValue("15");
-    Term v3 = d_solver.mkAbstractValue("18446744073709551617");
-
-    assertTrue(v1.isAbstractValue());
-    assertTrue(v2.isAbstractValue());
-    assertTrue(v3.isAbstractValue());
-    assertEquals("1", v1.getAbstractValue());
-    assertEquals("15", v2.getAbstractValue());
-    assertEquals("18446744073709551617", v3.getAbstractValue());
-  }
-
-  @Test void getTuple()
-  {
-    Sort s1 = d_solver.getIntegerSort();
-    Sort s2 = d_solver.getRealSort();
-    Sort s3 = d_solver.getStringSort();
-
-    Term t1 = d_solver.mkInteger(15);
-    Term t2 = d_solver.mkReal(17, 25);
-    Term t3 = d_solver.mkString("abc");
-
-    Term tup = d_solver.mkTuple(new Sort[] {s1, s2, s3}, new Term[] {t1, t2, t3});
-
-    assertTrue(tup.isTupleValue());
-    assertEquals(Arrays.asList((new Term[] {t1, t2, t3})), Arrays.asList(tup.getTupleValue()));
-  }
-
-  @Test void getFloatingPoint() throws CVC5ApiException
-  {
-    Term bvval = d_solver.mkBitVector(16, "0000110000000011", 2);
-    Term fp = d_solver.mkFloatingPoint(5, 11, bvval);
-
-    assertTrue(fp.isFloatingPointValue());
-    assertFalse(fp.isFloatingPointPosZero());
-    assertFalse(fp.isFloatingPointNegZero());
-    assertFalse(fp.isFloatingPointPosInf());
-    assertFalse(fp.isFloatingPointNegInf());
-    assertFalse(fp.isFloatingPointNaN());
-    assertEquals(new Triplet<Long, Long, Term>(5L, 11L, bvval), fp.getFloatingPointValue());
-
-    assertTrue(d_solver.mkPosZero(5, 11).isFloatingPointPosZero());
-    assertTrue(d_solver.mkNegZero(5, 11).isFloatingPointNegZero());
-    assertTrue(d_solver.mkPosInf(5, 11).isFloatingPointPosInf());
-    assertTrue(d_solver.mkNegInf(5, 11).isFloatingPointNegInf());
-    assertTrue(d_solver.mkNaN(5, 11).isFloatingPointNaN());
-  }
-
-  @Test void getSet()
-  {
-    Sort s = d_solver.mkSetSort(d_solver.getIntegerSort());
-
-    Term i1 = d_solver.mkInteger(5);
-    Term i2 = d_solver.mkInteger(7);
-
-    Term s1 = d_solver.mkEmptySet(s);
-    Term s2 = d_solver.mkTerm(Kind.SINGLETON, i1);
-    Term s3 = d_solver.mkTerm(Kind.SINGLETON, i1);
-    Term s4 = d_solver.mkTerm(Kind.SINGLETON, i2);
-    Term s5 = d_solver.mkTerm(Kind.UNION, s2, d_solver.mkTerm(Kind.UNION, s3, s4));
-
-    assertTrue(s1.isSetValue());
-    assertTrue(s2.isSetValue());
-    assertTrue(s3.isSetValue());
-    assertTrue(s4.isSetValue());
-    assertFalse(s5.isSetValue());
-    s5 = d_solver.simplify(s5);
-    assertTrue(s5.isSetValue());
-
-    assertSetsEquality(new Term[] {}, s1.getSetValue());
-    assertSetsEquality(new Term[] {i1}, s2.getSetValue());
-    assertSetsEquality(new Term[] {i1}, s3.getSetValue());
-    assertSetsEquality(new Term[] {i2}, s4.getSetValue());
-    assertSetsEquality(new Term[] {i1, i2}, s5.getSetValue());
-  }
-
-  private void assertSetsEquality(Term[] A, Set<Term> B)
-  {
-    List<Term> a = Arrays.stream(A).sorted().collect(Collectors.toList());
-    List<Term> b = B.stream().sorted().collect(Collectors.toList());
-    assertEquals(a, b);
-  }
-
-  @Test void getSequence()
-  {
-    Sort s = d_solver.mkSequenceSort(d_solver.getIntegerSort());
-
-    Term i1 = d_solver.mkInteger(5);
-    Term i2 = d_solver.mkInteger(7);
-
-    Term s1 = d_solver.mkEmptySequence(s);
-    Term s2 = d_solver.mkTerm(Kind.SEQ_UNIT, i1);
-    Term s3 = d_solver.mkTerm(Kind.SEQ_UNIT, i1);
-    Term s4 = d_solver.mkTerm(Kind.SEQ_UNIT, i2);
-    Term s5 = d_solver.mkTerm(Kind.SEQ_CONCAT, s2, d_solver.mkTerm(Kind.SEQ_CONCAT, s3, s4));
-
-    assertTrue(s1.isSequenceValue());
-    assertTrue(!s2.isSequenceValue());
-    assertTrue(!s3.isSequenceValue());
-    assertTrue(!s4.isSequenceValue());
-    assertTrue(!s5.isSequenceValue());
-
-    s2 = d_solver.simplify(s2);
-    s3 = d_solver.simplify(s3);
-    s4 = d_solver.simplify(s4);
-    s5 = d_solver.simplify(s5);
-
-    assertEquals(Arrays.asList(new Term[] {}), Arrays.asList(s1.getSequenceValue()));
-    assertEquals(Arrays.asList(new Term[] {i1}), Arrays.asList(s2.getSequenceValue()));
-    assertEquals(Arrays.asList(new Term[] {i1}), Arrays.asList(s3.getSequenceValue()));
-    assertEquals(Arrays.asList(new Term[] {i2}), Arrays.asList(s4.getSequenceValue()));
-    assertEquals(Arrays.asList(new Term[] {i1, i1, i2}), Arrays.asList(s5.getSequenceValue()));
-  }
-
-  @Test void getUninterpretedConst() throws CVC5ApiException
-  {
-    Sort s = d_solver.mkUninterpretedSort("test");
-    Term t1 = d_solver.mkUninterpretedConst(s, 3);
-    Term t2 = d_solver.mkUninterpretedConst(s, 5);
-
-    assertTrue(t1.isUninterpretedValue());
-    assertTrue(t2.isUninterpretedValue());
-
-    assertEquals(new Pair<Sort, Integer>(s, 3), t1.getUninterpretedValue());
-    assertEquals(new Pair<Sort, Integer>(s, 5), t2.getUninterpretedValue());
-  }
-
-  @Test void substitute()
-  {
-    Term x = d_solver.mkConst(d_solver.getIntegerSort(), "x");
-    Term one = d_solver.mkInteger(1);
-    Term ttrue = d_solver.mkTrue();
-    Term xpx = d_solver.mkTerm(PLUS, x, x);
-    Term onepone = d_solver.mkTerm(PLUS, one, one);
-
-    assertEquals(xpx.substitute(x, one), onepone);
-    assertEquals(onepone.substitute(one, x), xpx);
-    // incorrect due to type
-    assertThrows(CVC5ApiException.class, () -> xpx.substitute(one, ttrue));
-
-    // simultaneous substitution
-    Term y = d_solver.mkConst(d_solver.getIntegerSort(), "y");
-    Term xpy = d_solver.mkTerm(PLUS, x, y);
-    Term xpone = d_solver.mkTerm(PLUS, y, one);
-    List<Term> es = new ArrayList<>();
-    List<Term> rs = new ArrayList<>();
-    es.add(x);
-    rs.add(y);
-    es.add(y);
-    rs.add(one);
-    assertEquals(xpy.substitute(es, rs), xpone);
-
-    // incorrect substitution due to arity
-    rs.remove(rs.size() - 1);
-    assertThrows(CVC5ApiException.class, () -> xpy.substitute(es, rs));
-
-    // incorrect substitution due to types
-    rs.add(ttrue);
-    assertThrows(CVC5ApiException.class, () -> xpy.substitute(es, rs));
-
-    // null cannot substitute
-    Term tnull = d_solver.getNullTerm();
-    assertThrows(CVC5ApiException.class, () -> tnull.substitute(one, x));
-    assertThrows(CVC5ApiException.class, () -> xpx.substitute(tnull, x));
-    assertThrows(CVC5ApiException.class, () -> xpx.substitute(x, tnull));
-    rs.remove(rs.size() - 1);
-    rs.add(tnull);
-    assertThrows(CVC5ApiException.class, () -> xpy.substitute(es, rs));
-    es.clear();
-    rs.clear();
-    es.add(x);
-    rs.add(y);
-    assertThrows(CVC5ApiException.class, () -> tnull.substitute(es, rs));
-    es.add(tnull);
-    rs.add(one);
-    assertThrows(CVC5ApiException.class, () -> xpx.substitute(es, rs));
-  }
-
-  @Test void constArray() throws CVC5ApiException
-  {
-    Sort intsort = d_solver.getIntegerSort();
-    Sort arrsort = d_solver.mkArraySort(intsort, intsort);
-    Term a = d_solver.mkConst(arrsort, "a");
-    Term one = d_solver.mkInteger(1);
-    Term constarr = d_solver.mkConstArray(arrsort, one);
-
-    assertEquals(constarr.getKind(), CONST_ARRAY);
-    assertEquals(constarr.getConstArrayBase(), one);
-    assertThrows(CVC5ApiException.class, () -> a.getConstArrayBase());
-
-    arrsort = d_solver.mkArraySort(d_solver.getRealSort(), d_solver.getRealSort());
-    Term zero_array = d_solver.mkConstArray(arrsort, d_solver.mkReal(0));
-    Term stores = d_solver.mkTerm(STORE, zero_array, d_solver.mkReal(1), d_solver.mkReal(2));
-    stores = d_solver.mkTerm(STORE, stores, d_solver.mkReal(2), d_solver.mkReal(3));
-    stores = d_solver.mkTerm(STORE, stores, d_solver.mkReal(4), d_solver.mkReal(5));
-  }
-
-  @Test void getSequenceValue() throws CVC5ApiException
-  {
-    Sort realsort = d_solver.getRealSort();
-    Sort seqsort = d_solver.mkSequenceSort(realsort);
-    Term s = d_solver.mkEmptySequence(seqsort);
-
-    assertEquals(s.getKind(), CONST_SEQUENCE);
-    // empty sequence has zero elements
-    Term[] cs = s.getSequenceValue();
-    assertTrue(cs.length == 0);
-
-    // A seq.unit app is not a constant sequence (regardless of whether it is
-    // applied to a constant).
-    Term su = d_solver.mkTerm(SEQ_UNIT, d_solver.mkReal(1));
-    assertThrows(CVC5ApiException.class, () -> su.getSequenceValue());
-  }
-
-  @Test void termScopedToString()
-  {
-    Sort intsort = d_solver.getIntegerSort();
-    Term x = d_solver.mkConst(intsort, "x");
-    assertEquals(x.toString(), "x");
-    Solver solver2;
-    assertEquals(x.toString(), "x");
-  }
-}